[英]Java Swing create Oval by Click
我认为用java创建一个小程序很容易:
所以我做了什么:
然后发生了一些令人震惊的事情:我点击了我的jFrame ...什么也没发生。 我以为:好吧,让我们在创建新圈子后重新粉刷...但是什么也没发生! 仅当我单击windwos边框并重新拉伸它时,它才能“重新绘制”它。
同时还使我感到非常难过和难过的是,如果我单击某个位置,然后单击另一个位置,然后重新拉伸框架,则它只会绘制最后一个圆圈:(它应该同时绘制两个!)
现在我将repaint()放在了数千个不同的地方,但是没有区别。 我还尝试了setopaque等技术,只是因为我现在不知道该怎么办!
这里是mouseListener:您可以忽略颜色
public class Aufgabe3 {
public static Circ.CircleColor actualColor = CircleColor.ROT;
// fromone color to another depend on the actual
public static Circ.CircleColor getNextColor(Circ.CircleColor aktuell) {
switch (aktuell) {
case ROT:
return Circ.CircleColor.GRÜN;
case GRÜN:
return Circ.CircleColor.GELB;
case GELB:
return Circ.CircleColor.ROT;
default:
return null;
}
}
public static void main(String[] args) {
JFrame jFrame = new JFrame();
jFrame.setVisible(true);
jFrame.setSize(500, 500);
jFrame.setDefaultCloseOperation(jFrame.EXIT_ON_CLOSE);
// jFrame.add()
// farbenfolge rot,grün,gelb--
jFrame.addMouseListener(new MouseListener() {
@Override
public void mouseReleased(MouseEvent e) {
// TODO Auto-generated method stub
}
@Override
public void mousePressed(MouseEvent e) {
// TODO Auto-generated method stub
}
@Override
public void mouseExited(MouseEvent e) {
// TODO Auto-generated method stub
}
@Override
public void mouseEntered(MouseEvent e) {
// TODO Auto-generated method stub
}
@Override
public void mouseClicked(MouseEvent e) {
System.out.println("clicked");
int x = e.getX();
int y = e.getY();
System.out.println("coords:" + x + "|" + y);
Circ circ = new Circ(x, y, actualColor);
circ.repaint();
jFrame.add(circ);
jFrame.repaint();
System.out.println(actualColor);
// actualisation of the next color
actualColor = getNextColor(actualColor);
}
});
}
}
现在是圆:
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import javax.swing.JComponent;
import javax.swing.JPanel;
public class Circ extends JComponent {
static public enum CircleColor {
ROT, GRÜN, GELB
};
private int x;
private int y;
private CircleColor circleColor;
public Circ() {
super();
}
public Circ(int x, int y, CircleColor circColor) {
super();
this.x = x;
this.y = y;
this.circleColor = circColor;
System.out.println("new circle created");
setSize(new Dimension(50, 50));
setVisible(true);
setOpaque(true);
}
public Color decodeCircleColor(CircleColor farbe) {
switch (farbe) {
case GRÜN:
return Color.GREEN;
case GELB:
return Color.yellow;
case ROT:
return Color.red;
default:
return null;
}
}
@Override
protected void paintComponent(Graphics g) {
System.out.println("paint");
Graphics2D g2d = (Graphics2D) g;
super.paintComponent(g2d);
g2d.setColor(decodeCircleColor(circleColor));
// g2d.drawOval(x, y, 50, 50);
g2d.fillOval(x, y, 50, 50);
}
}
JFrame
的默认布局是BorderLayout
。 在不指定位置的情况下将组件添加到BorderLayout
,它们将被添加到BorderLayout.CENTER
从而替换了先前设置为此位置的组件。 这意味着您始终只将一个Circle
添加到您的JFrame中。
无论如何,您似乎都试图在光标的位置绘制圆,这意味着您必须将Circle
组件添加到JFrame
的不同位置,这并不容易。 取而代之的是,最好只在框架中添加一个组件并绘制该组件中的所有圆。
如果将组件添加到mouseClicked
事件中,则可能会重新验证应该调用的内容,因为更改了容器( JFrame
)。 而且,JFrame非常特殊:它们具有内容窗格 ,您应该通过以下方式添加组件:
frame.getContentPane().add(...);
默认的内容窗格使用BorderLayout
。
每次单击添加一个组件可能会过大,除非将其设置为null
(例如,绝对布局)并为每个圆调用setBounds(x,y,50,50),否则布局会有问题。
但是,由于您覆盖了paintComponent
,因此可以直接绘制椭圆,而不必关心布局或组件。
使用BorderLayout.CENTER约束添加一次Circle
组件。 这将确保您的Circle
能够获得最大尺寸。
MouseListener
应该位于Circle上,并且必须使其具有焦点( setFocus(true)
)。
每次在Circle
上单击鼠标时,将鼠标位置注册在列表中(例如: List<Point>
),然后调用repaint:
circle.points.add(new Point(e.getX(), e.getY()); //
circle.repaint();
每次调用paintComponent(Graphics)
,请使用列表按其调用顺序绘制椭圆。
@Override
protected void paintComponent(Graphics g) {
System.out.println("paint");
Graphics2D g2d = (Graphics2D) g;
super.paintComponent(g2d);
g2d.setColor(decodeCircleColor(circleColor));
// if you know lambda
points.forEach(p -> g2d.fillOval(p.x, p.y, 50, 50));
// or if you don't know lambda yet.
// for (Point p : points) g2d.fillOval(p.x, p.y, 50, 50));
}
请注意,您可以使用Point或任何相关类(例如,可以使用将存储Paint
对象的具体对象,例如java.awt.Color
来更改椭圆的颜色)。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.