在相同的图形中使用不同的颜色(Java)

  • 本文关键字:颜色 Java 图形 java
  • 更新时间 :
  • 英文 :


我对Java还比较陌生。

我需要做一个练习,用不同的位置和颜色画出不同的随机形状。我希望每个形状都有不同的颜色。这是我代码的一部分(有两种不同的形状,一种是椭圆形,另一种是矩形)。现在这两个形状有相同的随机颜色:

protected void paintComponent(Graphics g) {
  int R = (int)(Math.random()*256);
  int G = (int)(Math.random()*256);
  int B = (int)(Math.random()*256);
  Color color = new Color(R, G, B); // picks a random color
  int ovalA = (int)(Math.random()*400);
  int ovalB = (int)(Math.random()*300);
  int ovalC = (int)(Math.random()*(400 - ovalA));
  int ovalD = (int)(Math.random()*(300 - ovalB));
  int rectA = (int)(Math.random()*300);
  int rectB = (int)(Math.random()*400);
  int rectC = (int)(Math.random()*(400 - rectA));
  int rectD = (int)(Math.random()*(300 - rectB));
  super.paintComponent(g);
  g.setColor(color);
  g.fillOval(ovalA, ovalB, ovalC, ovalD);
  g.fillRect(rectA, rectB, rectC, rectD);

}

protected void paintComponent(Graphics g) {
  int R = (int)(Math.random()*256);
  int G = (int)(Math.random()*256);
  int B = (int)(Math.random()*256);
  Color color = new Color(R, G, B); // picks a random color
  g.setColor(color);
  int ovalA = (int)(Math.random()*400);
  int ovalB = (int)(Math.random()*300);
  int ovalC = (int)(Math.random()*(400 - ovalA));
  int ovalD = (int)(Math.random()*(300 - ovalB));
  g.fillOval(ovalA, ovalB, ovalC, ovalD);

  R = (int)(Math.random()*256);
  G = (int)(Math.random()*256);
  B = (int)(Math.random()*256);
  color = new Color(R, G, B); // picks a random color
  int rectA = (int)(Math.random()*300);
  int rectB = (int)(Math.random()*400);
  int rectC = (int)(Math.random()*(400 - rectA));
  int rectD = (int)(Math.random()*(300 - rectB));
  super.paintComponent(g);
  g.setColor(color);
  g.fillRect(rectA, rectB, rectC, rectD);
}

现在,这是它背后的解释,当你按照你的方式编码时,你没有得到一组新的随机数字来表示你的颜色,即使你要求颜色,你使用的int也保持不变。我只是用math.random再次更改了这些值,然后用

p>目前,您正在为两个形状使用相同的Color对象。您必须为每个应该用新颜色绘制的形状创建一个新的Color对象。

我建议为此设置一个实用方法。这种方法大致如下所示:

private static final Random random = new Random(0);
private static Color createRandomColor() {
    int r = random.nextInt(256);
    int g = random.nextInt(256);
    int b = random.nextInt(256);
    Color color = new Color(r, g, b);
    return color;
}

通过这种方式,您可以轻松绘制具有不同随机颜色的形状:

g.setColor(createRandomColor());
g.fillOval(ovalA, ovalB, ovalC, ovalD);
g.setColor(createRandomColor());
g.fillRect(rectA, rectB, rectC, rectD);

旁白:我通常建议使用java.util.Random而不是Math.random。主要原因是java.util.Random提供了一些实用的方法,比如上面方法中使用的nextInt方法,在这里非常方便。此外,Random实例可以使用特定的种子创建,然后将始终返回相同的随机数序列,这可以使调试变得更容易(事实上,在某些情况下,只有这样才能使调试甚至成为可能!)。如果您再次想要"真实"随机数,您可以简单地创建Random实例,而不需要种子。


编辑:Kevin Workman在他的评论中提出了一个重要的观点:

此外,您可能应该在paintComponent()方法之外初始化随机颜色,这样它就不会在每次重新绘制组件时发生变化。

但是,由于在每次调用paintComponent期间,您也在随机创建形状,因此在调整窗口大小时,所有内容都会闪烁。

通常,paintComponent方法应油漆。不应在那里读取或创建任何数据。对于您的应用程序案例,您可以通过创建包含Shape对象的List以及包含Color对象的列表来解决此问题。我稍后将在这里添加一个示例。

编辑2:下面是一个例子:

import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Shape;
import java.awt.geom.Ellipse2D;
import java.awt.geom.Rectangle2D;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
public class RandomShapePainter
{
    public static void main(String[] args)
    {
        SwingUtilities.invokeLater(new Runnable()
        {
            @Override
            public void run()
            {
                createAndShowGUI();
            }
        });
    }
    private static void createAndShowGUI()
    {
        JFrame f = new JFrame();
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        f.getContentPane().add(new RandomShapePanel());
        f.setSize(600,600);
        f.setLocationRelativeTo(null);
        f.setVisible(true);
    }
}
class RandomShapePanel extends JPanel
{
    private final List<Shape> shapes;
    private final List<Color> colors;
    private static final Random random = new Random(0);
    RandomShapePanel()
    {
        shapes = new ArrayList<Shape>();
        colors = new ArrayList<Color>();
        for (int i=0; i<5; i++)
        {
            shapes.add(createRandomShape());
            colors.add(createRandomColor());
        }
    }
    private static Shape createRandomShape()
    {
        boolean b = random.nextBoolean();
        if (b)
        {
            return createRandomOval();
        }
        return createRandomRectangle();
    }
    private static Shape createRandomOval()
    {
        // Hard-coded constants should be avoided,
        // just for illustration here
        double x = 100+random.nextInt(300);
        double y = 100+random.nextInt(300);
        double w = 100+random.nextInt(300);
        double h = 100+random.nextInt(300);
        return new Ellipse2D.Double(x, y, w, h);
    }
    private static Shape createRandomRectangle()
    {
        // Hard-coded constants should be avoided,
        // just for illustration here
        double x = 100+random.nextInt(300);
        double y = 100+random.nextInt(300);
        double w = 100+random.nextInt(300);
        double h = 100+random.nextInt(300);
        return new Rectangle2D.Double(x, y, w, h);
    }
    private static Color createRandomColor() 
    {
        int r = random.nextInt(256);
        int g = random.nextInt(256);
        int b = random.nextInt(256);
        Color color = new Color(r, g, b);
        return color;
    }    

    @Override
    protected void paintComponent(Graphics gr)
    {
        super.paintComponent(gr);
        Graphics2D g = (Graphics2D)gr;
        for (int i=0; i<shapes.size(); i++)
        {
            Shape shape = shapes.get(i);
            Color color = colors.get(i);
            g.setColor(color);
            g.fill(shape);
        }
    }
}

最新更新