How can i make the size of ellipse keeps the size after i released the mouse - processing

what I need to do is:
As long as the mouse is still pressed, the shapes get smaller and smaller with each frame (already complete it)
When the mouse is released, the shapes keep their size.
When the mouse has clicked again, the „explosion“ is reset (i.e. all shapes that are still visible from the previous explosion vanish and the explosion starts again).
float gravity = .4;
int particle_each_time = 4;
ArrayList<Particle> particle= new ArrayList(); // ArrayList to manage to list of all particles
void setup() {
size(640, 480);
}
void draw() {
background(0);
for (int i = 0; i < particle_each_time; i++) {
particle.add(new Particle(mouseX, mouseY));
}
for (int i = 0; i < particle.size(); i++) {
Particle p = particle.get(i);
p.update(gravity);
p.draw();
}
}
//Next tab
class Particle {
float x; //X Position
float y; //Y Position
float velX; //velocity on X axis
float velY; //velocity on Y axis
float size; // Size of the particle
// float sizeFromMouse;
float lifespan; // duration of the particle
float col;//create fire type colours
Particle(float x, float y) {
this.velY = random(-10, 10);
this.velX = random(-10, 10);
this.x = x;
this.y = y;
this.size = 20;
lifespan = 220.0;
col = random(#DE8816);
}
void update(float gravity) {
this.x += velX; // direction of X axis
velY += gravity; // gravity affectiing the velocity on Y axis causing to fall
this.y += velY; //direction of Y axis
lifespan -= 1.0;
if (mousePressed ) {
size = size - 0.51;
}
if (size<0) {
size = 1;
}
}
boolean isDead() {
if (lifespan < 0.0) {
return true;
} else {
return false;
}
}
void draw() {
stroke(0, lifespan);
fill(#DE8816, lifespan);
ellipse(x, y, size, size);
}
}

Related

in Processing, how to hover over mouse to make numbers of rectangles change color?

I've finished a single rectangle code, but I'd like to know ways to make at least four rectangles change color while hovering the mouse over them. Any advice is much appreciated.
code is below:
int rectX, rectY;
int rectSize = 90;
color rectColor;
color baseColor;
boolean rectOver = false;
void setup() {
size(640, 360);
rectColor = color(0);
baseColor = color(102);
rectX = width/2;
rectY = height/2;
rectMode(CENTER);
}
void draw() {
update(mouseX, mouseY);
noStroke();
if (rectOver) {
rectColor = color(255);
}else
{
rectColor = color(0);
}
stroke(255);
fill(rectColor);
rect(rectX, rectY, rectSize, rectSize);
}
void update(int x, int y) {
if ( overRect(rectX, rectY, rectSize, rectSize) ) {
rectOver = true;}
else{rectOver = false;}
}
boolean overRect(int x, int y, int width, int height) {
if (mouseX >= x-width/2 && mouseX <= x+width/2 &&
mouseY >= y-height/2 && mouseY <= y+height/2) {
return true;
}
else {
return false;
}
}
First of all, you have to fix your overRect function since width and height are built-in variables, secondly what you need to do is to declare a rectangle class that will contain the x,y, width and height of your rectangle, plus two methods: one to check if the mouse if hovering (using your old method) and one to self draw the rectangle. Lastly, you need an array to store your rectangles. Here is the final code:
int rectX, rectY;
int rectSize = 90;
color rectColor;
color baseColor;
ArrayList<rectangle> list;
boolean rectOver = false;
class rectangle {
float x,y,w,h;
rectangle (float y, float x,float w, float h) {
this.x = x;
this.y = y;
this.w = w;
this.h = h;
}
boolean checkInside() {
return overRect(x,y,w,h);
}
void selfDraw(){
if (this.checkInside()) {
rectColor = color(255);
}else
{
rectColor = color(0);
}
stroke(255);
fill(rectColor);
rect(x, y, w, h);
}
}
void setup() {
size(640, 360);
rectMode(CENTER);
list= new ArrayList<rectangle>();
list.add(new rectangle(40,40,50,60));
list.add(new rectangle(20,200,50,20));
list.add(new rectangle(300,200,50,50));
list.add(new rectangle(200,300,80,60));
}
void draw() {
for (int i = 0; i < list.size(); i++) {
list.get(i).selfDraw();
}
}
boolean overRect(float x, float y, float w, float h) {
if (mouseX >= x-w/2 && mouseX <= x+w/2 &&
mouseY >= y-h/2 && mouseY <= y+h/2) {
return true;
}
else {
return false;
}
}
Use inheritence. As in YOUSFI's answer, your nest net would be to build a rectangle class and write it's own mouse over function in there. Then, you can make an instance of that object in your main program and call it's mouseover function.
Instead of blindly copy pasting the code YOUSFI provided, my suggestion would be to read up on Object Oriented Programming or watch this introductory video series: https://www.youtube.com/watch?v=xG2Vbnv0wvg

object releases another smaller object?

Can anyone help me?
So, I'm supposed to have a ball that is moving horizontally, such that every time I press the mouse, a ball would get shoot vertically, then slows down due to friction. The vertical ball would stay in the old position but the player would reset.
How do I go about doing that without using classes?
Here my code so far:
boolean circleupdatetostop = true;
float x = 100;
float yshot = 880;
float speedshot = random(4,10);
float speedx = 6;
void setup() {
size(1280,960);
}
void draw() {
background(255);
stroke(0);
fill(0);
circle(x,880,80);
if (x > width || x < 0 ) {
speedx = speedx * -1;
}
if (circleupdatetostop) {
x = x + speedx;
}
if (circleupdatetostop == false) {
float locationx = x;
stroke(0);
fill(255,0,255);
circle(locationx,yshot,30);
yshot = yshot - speedshot;
}
}
void mousePressed () {
circleupdatetostop = !circleupdatetostop;
}
I'm not entirely sure if this is what you meant, but you could achieve shooting multiple balls by using ArrayList as well as processing's PVector to better handle the x and y coordinate pairs. If you wanted to look at classes, see this post.
import java.util.*;
// Whether the ball is moving or not
boolean circleupdatetostop = true;
// Information about the main_ball
PVector position = new PVector(100, 880);
PVector speed = new PVector(6, 0);
float diameter = 80;
// Information about the sot balls
ArrayList<PVector> balls_loc = new ArrayList<PVector>();
ArrayList<PVector> balls_speed = new ArrayList<PVector>();
float diameter_shot = 30;
float friction = 0.994;
void setup() {
size(1280, 960);
}
void draw() {
background(255);
stroke(0);
fill(0);
circle(position.x, position.y, diameter);
// Remember to consider the radius of the ball when bouncing off the edges
if (position.x + diameter/2 > width || position.x - diameter/2 < 0 ) {
speed.mult(-1);
}
if (circleupdatetostop) {
position.add(speed);
}
// Cycle through the list updating their speed and draw each ball
for (int i = 0; i<balls_loc.size(); i++) {
balls_speed.get(i).mult(friction+random(-0.05, 0.05));
balls_loc.get(i).add(balls_speed.get(i));
stroke(0);
fill(255, 0, 255);
circle(balls_loc.get(i).x, balls_loc.get(i).y, diameter_shot);
}
}
void mousePressed(){
// Add a new ball to be drawn
if(circleupdatetostop){
balls_loc.add(new PVector(position.x, position.y));
balls_speed.add(new PVector(0, random(-4, -10)));
}
circleupdatetostop = !circleupdatetostop;
}

Trying to make a ball bounce on the screen in processing using classes

I am working on making a single ball bounce all over the screen but I have an issue with making the ball bounce the bounce() function is responsible for making the ball bounce but I run into an array out of bounds exception despite only going through 1 element in the array. I have provided the code below. This code utilizes 2 classes (Ball_Usage and Ball).
Ball_Usage code:
Ball ball1;
void setup(){
size(500,500);
ball1 = new Ball();
}
void draw(){
background(255);
ball1.bounce();
}
Ball:
class Ball{
float [] xPos = {};
float [] yPos = {};
float [] dia = {};
float [] xSpeed = {};
float [] ySpeed = {};
Ball(){
}
Ball(float x, float y, float argDia){
xPos = append(xPos, x);
yPos = append(yPos, y);
dia = append(dia, argDia);
}
void bounce(){
for(int i=0; i<1; i++){
ellipse(xPos[i], yPos[i], 50, 50);
xPos[i] += xSpeed[i];
yPos[i] += ySpeed[i];
if(xPos[i]<0 || xPos[i]>=width){
xSpeed[i] = -xSpeed[i];
}
if(yPos[i]<0 || yPos[i]>=height){
ySpeed[i] = -ySpeed[i];
}
}
}
}
I believe the confusion comes from the fact that your class has two constructors:
an empty constructor (that takes no arguments): Ball()
a constructor with position and argDia (guessing diameter ?) arguments: Ball(float x, float y, float argDia)
In setup() you call the empty constructor:
ball1 = new Ball();
This means the five float arrays still have a length of 0, hence the out of bounds exception.
Even if you call the position + diameter version of the constructor, the xSpeed, ySpeed arrays will still have length 0.
You could fix this by initialising the two two arrays as well as using this version of the constructor:
Ball ball1;
void setup() {
size(500, 500);
//ball1 = new Ball();
ball1 = new Ball(250, 250, 50);
}
void draw() {
background(255);
ball1.bounce();
}
class Ball {
float [] xPos = {};
float [] yPos = {};
float [] dia = {};
float [] xSpeed = {};
float [] ySpeed = {};
Ball() {
}
Ball(float x, float y, float argDia) {
xPos = append(xPos, x);
yPos = append(yPos, y);
dia = append(dia, argDia);
xSpeed = append(xSpeed, random(-1, 1));
ySpeed = append(ySpeed, random(-1, 1));
}
void bounce() {
for (int i=0; i<1; i++) {
ellipse(xPos[i], yPos[i], 50, 50);
xPos[i] += xSpeed[i];
yPos[i] += ySpeed[i];
if (xPos[i]<0 || xPos[i]>=width) {
xSpeed[i] = -xSpeed[i];
}
if (yPos[i]<0 || yPos[i]>=height) {
ySpeed[i] = -ySpeed[i];
}
}
}
}
This will work, however there is still a bit of confusion: why use the arrays at all if you're only looping once for the first element ? It makes the arrays and for loop mostly redundant.
You might choose to keep if you plan to change the diameter over time (which in your code is hardcoded to 50), maybe positions and velocities and render a changing history of a ball.
If you don't, you could simply use float properties instead of arrays:
Ball ball1;
void setup() {
size(500, 500);
ball1 = new Ball();
}
void draw() {
background(255);
ball1.bounce();
}
class Ball {
float xPos;
float yPos;
float diameter = 50;
float xSpeed;
float ySpeed;
Ball() {
xPos = width / 2;
yPos = height / 2;
xSpeed = random(-1, 1);
ySpeed = random(-1, 1);
}
void bounce() {
ellipse(xPos, yPos, diameter, diameter);
xPos += xSpeed;
yPos += ySpeed;
if (xPos < 0 || xPos >= width) {
xSpeed = -xSpeed;
}
if (yPos < 0 || yPos >= height) {
ySpeed = -ySpeed;
}
}
}
This looks more similar to the Bounce Processing Example.
You can at a later stage make an array of Ball objects.
Additionally it's worth formatting code as it saves you time reading/scrolling through it and visually it's easier to scan the structure of the program (how each part fits in) and therefore makes it easier to debug/run mentally. It takes no effort as you can simply press Ctrl+T on Windows/Linux or CMD+T on OSX. On the long run this will pay off, especially as programs get longer and more complex as you spend more time reading code than writing code. It's a good habit to pickup early while learning to code. Have fun!

Processing: How can I make multiple elements in a for() loop move to one location then return?

I have a grid of ellipses generated by two for() loops. What I'd like to do is have all of these ellipses ease into mouseX and mouseY when mousePressed == true, otherwise return to their position in the grid. How can I go about this? I've started with this template, which doesn't work as I can't figure out how affect the position of the ellipses, but the easing is set up.
float x;
float y;
float easeIn = 0.01;
float easeOut = 0.08;
float targetX;
float targetY;
void setup() {
size(700, 700);
pixelDensity(2);
background(255);
noStroke();
}
void draw() {
fill(255, 255, 255, 80);
rect(0, 0, width, height);
for (int i = 50; i < width-50; i += 30) {
for (int j = 50; j < height-50; j += 30) {
fill(0, 0, 0);
ellipse(i, j, 5, 5);
if (mousePressed == true) {
// go to mouseX
targetX = mouseX;
// ease in
float dx = targetX - x;
if (abs(dx) > 1) {
x += dx * easeIn;
}
//go to mouseY
targetY = mouseY;
// ease in
float dy = targetY - y;
if (abs(dy) > 1) {
y += dy * easeIn;
}
} else {
// return to grid
targetX = i;
// ease out
float dx = targetX - x;
if (abs(dx) > 1) {
x += dx * easeOut;
}
// return to grid
targetY = j;
// ease out
float dy = targetY - y;
if (abs(dy) > 1) {
y += dy * easeOut;
}
}
}
}
}
Any help would be greatly appreciated. I'm not sure in which order to do things/which elements should be contained in the loop.
Thanks!
You're going to have to keep track of a few things for each dot: its "home" position, its current position,its speed, etc.
The easiest way to do this would be to create a class that encapsulates all of that information for a single dot. Then you'd just need an ArrayList of instances of the class, and iterate over them to update or draw them.
Here's an example:
ArrayList<Dot> dots = new ArrayList<Dot>();
void setup() {
size(700, 700);
background(255);
noStroke();
//create your Dots
for (int i = 50; i < width-50; i += 30) {
for (int j = 50; j < height-50; j += 30) {
dots.add(new Dot(i, j));
}
}
}
void draw() {
background(255);
//iterate over your Dots and move and draw each
for (Dot dot : dots) {
dot.stepAndRender();
}
}
class Dot {
//the point to return to when the mouse is not pressed
float homeX;
float homeY;
//current position
float currentX;
float currentY;
public Dot(float homeX, float homeY) {
this.homeX = homeX;
this.homeY = homeY;
currentX = homeX;
currentY = homeY;
}
void stepAndRender() {
if (mousePressed) {
//use a weighted average to chase the mouse
//you could use whatever logic you want here
currentX = (mouseX+currentX*99)/100;
currentY = (mouseY+currentY*99)/100;
} else {
//use a weighted average to return home
//you could use whatever logic you want here
currentX = (homeX+currentX*99)/100;
currentY = (homeY+currentY*99)/100;
}
//draw the ellipse
fill(0, 0, 0);
ellipse(currentX, currentY, 5, 5);
}
}
Note that I'm just using a weighted average to determine the position of each ellipse, but you could change that to whatever you want. You could give each ellipse a different speed, or use your easing logic, whatever. But the idea is the same: encapsulate everything you need into a class, and then put the logic for one dot into that class.
I'd recommend getting this working for a single dot first, and then moving up to getting it working with multiple dots. Then if you have another question you can post the code for just a single dot instead of a bunch. Good luck.

Moving Generated Images Down in Processing Sketch

I'm new to Processing and want to make the following sketch move images down, rather than up. I have tried adjusting the y to y+= speed in void move(), which does this but the images don't reload, they just do one cycle and the screen goes blank.
Your help would be appreciated :-)
Spot[] sp = new Spot[60];
PImage myImage;
/* #pjs preload="http://mathatelle.appspot.com/imgs/drawing_circle.png"; */
void setup() {
size(800, 400);
imageMode(CENTER);
myImage = loadImage("http://mathatelle.appspot.com/imgs/drawing_circle.png"); //100x100px
for (int i = 0; i < sp.length; i++) {
sp[i] = new Spot(random(width), random(height), random(0.2,1.0), random(0.1,1.0));
}
}
void draw() {
background(0);
for (int i = 0; i < sp.length; i++) {
sp[i].move();
sp[i].display();
}
}
class Spot {
float x, y, diameter, speed; // x座標, y座標, 直径, 速さ
Spot(float _x, float _y, float _diameter, float _speed) {
x = _x;
y = _y;
diameter = _diameter;
speed = _speed;
}
void move() {
speed *= 1.01;
y -= speed;
if (y < - myImage.width*diameter/2) {
x = random(width);
y = height + myImage.width*diameter/2;
speed = random(0.5,3);
}
}
void display() {
pushMatrix();
translate(x, y);
rotate(TWO_PI*diameter);
scale(diameter);
//tint(255, 255, 255, 153);
image(myImage, 0, 0);
popMatrix();
}
}
The logical is kind of inverted already,but just invert it again :)
here there are comments in the code:
Spot[] sp = new Spot[60];
PImage myImage;
/* #pjs preload="http://mathatelle.appspot.com/imgs/drawing_circle.png"; */
void setup() {
size(800, 400);
imageMode(CENTER);
myImage = loadImage("http://mathatelle.appspot.com/imgs/drawing_circle.png"); //100x100px
for (int i = 0; i < sp.length; i++) {
// a little change where spots are created...
sp[i] = new Spot(random(width), random(-myImage.height, height - 100), random(0.2, 1.0), random(0.1, 1.0));
}
}
void draw() {
background(0);
for (int i = 0; i < sp.length; i++) {
sp[i].move();
sp[i].display();
}
}
class Spot {
float x, y, diameter, speed; // x座標, y座標, 直径, 速さ
Spot(float _x, float _y, float _diameter, float _speed) {
x = _x;
y = _y;
diameter = _diameter;
speed = _speed;
}
void move() {
speed *= 1.01;
// invert movement direction
y += speed;
// also invert the test...
if (y > height + myImage.width*diameter/2) {
x = random(width);
y = height + myImage.width*diameter/2;
speed = random(0.5, 3);
}
}
void display() {
pushMatrix();
translate(x, y);
rotate(TWO_PI*diameter);
scale(diameter);
//tint(255, 255, 255, 153);
image(myImage, 0, 0);
popMatrix();
}
}
A friend helped me out, this is the solution to my problem :-)
Spot[] sp = new Spot[60];
PImage myImage;
/* #pjs preload="http://mathatelle.appspot.com/imgs/drawing_circle.png"; */
void setup() {
size(800, 400);
imageMode(CENTER);
myImage = loadImage("http://mathatelle.appspot.com/imgs/drawing_circle.png"); //100x100px
for (int i = 0; i < sp.length; i++) {
// a little change where spots are created...
sp[i] = new Spot(random(width), random(-myImage.height, height - 100), random(0.2, 1.0), random(0.1, 1.0));
}
}
void draw() {
background(0);
for (int i = 0; i < sp.length; i++) {
sp[i].move();
sp[i].display();
}
}
class Spot {
float x, y, diameter, speed; // x座標, y座標, 直径, 速さ
Spot(float _x, float _y, float _diameter, float _speed) {
x = _x;
y = _y;
diameter = _diameter;
speed = _speed;
}
void move() {
speed *= 1.01;
y += speed;
// change y = 0 - ...
if (y > height + myImage.width*diameter/2) {
x = random(width);
y = 0 - myImage.width*diameter/2;
speed = random(0.5, 3);
}
}
void display() {
pushMatrix();
translate(x, y);
rotate(TWO_PI*diameter);
scale(diameter);
//tint(255, 255, 255, 153);
image(myImage, 0, 0);
popMatrix();
}
}

Resources