package de.mcs.test.graphics;
import java.awt.AlphaComposite;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Point;
import java.awt.RenderingHints;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
import javax.swing.JComponent;
import javax.swing.JFrame;
public class Balls extends JComponent implements Runnable {
private static final long serialVersionUID = 3224830373101405104L;
private int width;
private int height;
private List<Ball> balls;
private int ballsAmount = 10;
private int reloadTime = 30;
private boolean clicked;
private int explodingSize = 40;
private int explodingTime = 3000;
public Balls(int width, int height) {
super();
setPreferredSize(new Dimension(width, height));
addMouseListener(new MouseAdapter()
{
public void mousePressed(MouseEvent e)
{
if(!clicked)
{
Ball clickedBall = new Ball(0, new Point(0,0), new Point(e.getX(), e.getY()), Color.WHITE);
clickedBall.setExploding(true);
balls.add(clickedBall);
clicked = true;
}
}
});
this.width = width;
this.height = height;
initBalls(ballsAmount, 8);
startAnimation();
}
private void initBalls(int amount, int radius)
{
this.balls = new ArrayList<Ball>();
Random rand = new Random();
for(int i = 0; i < amount; i++)
{
Point speed = new Point(rand.nextInt(2)+1, rand.nextInt(2)+1);
Point position = new Point(rand.nextInt(width-radius*2), rand.nextInt(height-radius*2));
Color color = new Color(rand.nextInt(255), rand.nextInt(255), rand.nextInt(255));
this.balls.add(new Ball(radius, speed, position, color));
}
}
private void startAnimation() {
new Thread(this).start();
}
public void run() {
try {
while (!Thread.currentThread().isInterrupted()) {
for(int j = 0; j < balls.size(); j++)
{
Ball ball = balls.get(j);
ball.move();
ball.explosion();
if(ball.isExploding())
{
if(ball.radius == 0)
{
balls.remove(j);
System.out.println(balls.size());
continue;
}
for(int i = 0; i < balls.size(); i++)
{
Ball tmp = balls.get(i);
if(ball == tmp)
continue;
if(ball.checkCollision(tmp))
tmp.setExploding(true);
}
}
}
repaint();
Thread.sleep(reloadTime);
}
} catch (InterruptedException e) {
e.printStackTrace();
}
}
protected void paintComponent(Graphics g) {
Graphics2D g2d = (Graphics2D) g;
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g2d.setColor(new Color(0, 51, 51));
g2d.fillRect(0, 0, width, height);
for(Ball ball : balls)
ball.paint(g2d);
}
class Ball {
private int radius;
private Point speed;
private Point position;
private Color color;
private boolean exploding;
private int explodingCounter;
public Ball(int radius, Point speed, Point position, Color color) {
this.radius = radius;
this.speed = speed;
this.position = position;
this.color = color;
}
public void move() {
if(exploding)
return;
if((position.x-radius) < 0 || (position.x+radius) > width)
speed.x = -speed.x;
if((position.y-radius) < 0 || (position.y+radius) > height)
speed.y = -speed.y;
position.x += speed.x;
position.y += speed.y;
}
public void explosion()
{
if(!exploding)
return;
if(explodingCounter++ < explodingTime/reloadTime)
{
if(radius < explodingSize)
radius++;
}
else if(radius-- >= 1);
}
public boolean checkCollision(Ball ball)
{
return position.distance(ball.position) < (radius+ball.radius);
}
public void paint(Graphics2D g2d) {
AlphaComposite ac = AlphaComposite.getInstance(AlphaComposite.SRC_OVER, 0.5f);
g2d.setComposite(ac);
g2d.setColor(color);
g2d.fillOval(position.x-radius, position.y-radius, radius * 2, radius * 2);
}
public boolean isExploding() {
return exploding;
}
public void setExploding(boolean exploding) {
this.exploding = exploding;
if(exploding)
{
this.speed.x = 0;
this.speed.y = 0;
}
}
public void setRadius(int radius) {
this.radius = radius;
}
}
public static void main(String[] args) {
JFrame frame = new JFrame("Balls");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(new Balls(500, 350));
frame.pack();
frame.setVisible(true);
}
}