我正在开发一个Java屏幕保护程序项目,到目前为止,我已经完成了很多工作。我需要代码在随机位置生成随机颜色的随机形状。我相信我已经完成了所有随机方面的工作,但现在我只需要使用计时器以500 ms的间隔创建这些形状。我还需要创建一个计数器来计算30个形状,然后清除屏幕并重新开始。 (我有背景和keylistener为项目的其他部分添加,但他们工作得很完美,万一有人想知道他们为什么在那里)。
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
import java.util.Random;
public class ScreenSaver1 extends JPanel implements ActionListener {
private JFrame frame = new JFrame("FullSize");
private Rectangle rectangle;
Timer t;
int x1, y1;
boolean full;
protected void paintComponent(Graphics g) {
super.paintComponent(g);
int shape;
shape = (int)(Math.random() * 4);
}
ScreenSaver1() {
t = new Timer(500, this);
t.setDelay(500);
t.start();
// Remove the title bar, min, max, close stuff
frame.setUndecorated(true);
// Add a Key Listener to the frame
frame.addKeyListener(new KeyHandler());
// Add this panel object to the frame
frame.add(this);
// Get the dimensions of the screen
rectangle = GraphicsEnvironment.getLocalGraphicsEnvironment()
.getDefaultScreenDevice().getDefaultConfiguration().getBounds();
// Set the size of the frame to the size of the screen
frame.setSize(rectangle.width, rectangle.height);
frame.setVisible(true);
// Remember that we are currently at full size
full = true;
}
// This method will run when any key is pressed in the window
class KeyHandler extends KeyAdapter {
public void keyPressed(KeyEvent e) {
// Terminate the program.
if (e.getKeyChar() == 'x') {
System.out.println("Exiting");
System.exit(0);
}
else if (e.getKeyChar() == 'r') {
System.out.println("Change background color");
setBackground(new Color((int)(Math.random() * 256), (int)(Math.random() * 256), (int)(Math.random() * 256)));
repaint();
}
else if (e.getKeyChar() == 'z') {
System.out.println("Resizing");
frame.setSize((int)rectangle.getWidth() / 2, (int)rectangle.getHeight());
}
}
}
private void makeLine(Graphics g) {
int x = (int)(Math.random() * rectangle.getWidth());
int y = (int)(Math.random() * rectangle.getHeight());
int x1 = (int)(Math.random() * 100);
int y1 = (int)(Math.random() * 100);
g.setColor(new Color((int)(Math.random() * 256), (int)(Math.random() * 256), (int)(Math.random() * 256) ));
g.drawLine(x, y, x1, y1);
}
private void makeRect(Graphics g) {
int x = (int)(Math.random() * rectangle.getWidth());
int y = (int)(Math.random() * rectangle.getHeight());
int width = (int)(Math.random() * 100);
int height = (int)(Math.random() * 100);
g.setColor(new Color((int)(Math.random() * 256), (int)(Math.random() * 256), (int)(Math.random() * 256) ));
g.drawRect(x, y, width, height);
}
private void makeOval(Graphics g) {
int x = (int)(Math.random() * rectangle.getWidth());
int y = (int)(Math.random() * rectangle.getHeight());
int width = (int)(Math.random() * 100);
int height = (int)(Math.random() * 100);
g.setColor(new Color((int)(Math.random() * 256), (int)(Math.random() * 256), (int)(Math.random() * 256) ));
g.drawOval(x, y, width, height);
}
private void makeRoundRect(Graphics g) {
int x = (int)(Math.random() * rectangle.getWidth());
int y = (int)(Math.random() * rectangle.getHeight());
int width = (int)(Math.random() * 100);
int height = (int)(Math.random() * 100);
int arcWidth = (int)(Math.random() * width);
int arcHeight = (int)(Math.random() * height);
g.setColor(new Color((int)(Math.random() * 256), (int)(Math.random() * 256), (int)(Math.random() * 256) ));
g.drawRoundRect(x, y, width, height, arcWidth, arcHeight);
}
public static void main(String[] args) {
ScreenSaver1 obj = new ScreenSaver1();
}
}
答案 0 :(得分:7)
你不会喜欢我,但我会建议你稍微备份......
首先,Java提供了一个非常好的基本Shape
接口,它定义了应该如何呈现“形状”(以及其他内容),所以相反完全重新发明轮子,我建议你从此
接下来,您需要某种对象包含Shape
(包含位置和大小信息)和Color
,例如......
public class RandomShape {
private final Color color;
private final Shape shape;
public RandomShape(Color color, Shape shape) {
this.color = color;
this.shape = shape;
}
public Color getColor() {
return color;
}
public Shape getShape() {
return shape;
}
public void paint(Graphics2D g2d) {
g2d.setColor(color);
g2d.draw(shape);
g2d.fill(shape);
}
}
这甚至可以自己画画。
接下来,我会创建一个List
来包含这些形状......
private List<RandomShape> shapes;
这不仅可以作为您的计数器,还可以让您更新屏幕非常简单。当shapes
List
包含30个或更多项时,您只需将其清除并重新绘制屏幕即可...
接下来,您需要一个javax.swing.Timer
,用于触发更新......
这个计时器应该......
检查shapes
列表是否需要清除......
随机生成Color
...
int r = (int) (Math.random() * 255);
int g = (int) (Math.random() * 255);
int b = (int) (Math.random() * 255);
Color color = new Color(r, g, b);
随机生成形状的大小和位置......
int width = 10 + (int) (Math.random() * 40);
int height = 10 + (int) (Math.random() * 40);
int x = (int) (Math.random() * (getWidth() - width));
int y = (int) (Math.random() * (getHeight() - height));
随机生成基础基本形状......
Shape shape = null;
switch (whichShape) {
case 0:
shape = new Line2D.Double(x, y, x + width, y + height);
break;
case 1:
shape = new Rectangle2D.Double(x, y, width, height);
break;
case 2:
shape = new Ellipse2D.Double(x, y, width, height);
break;
}
创建RandomShape
,将其添加到列表中并重新绘制组件...
RandomShape randomShape = new RandomShape(color, shape);
shapes.add(randomShape);
repaint();
简单;)
现在,当您需要绘制组件时,只需遍历形状列表...
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g.create();
for (RandomShape shape : shapes) {
shape.paint(g2d);
}
g2d.dispose();
}
答案 1 :(得分:0)
查看Playing With Shapes以获取允许您将Shapes用作实际组件的方法。然后,您只需将组件添加到面板中,您就不必担心自定义绘画。
答案 2 :(得分:0)
您可以在不使用像这样的循环的情况下绘制所有形状
private void paintAllShapes(Graphics g, int n) {
if(n < shapes.size()) {
shapes.get(n).paint((Graphics2D)g);
paintAllShapes(g, n+1);
}
}
protected void paintComponent(Graphics g) {
super.paintComponent(g);
paintAllShapes(g, 0);
}