我想制作一个在屏幕上有对象的程序,然后当你按下它们时它将跟随鼠标指针,直到你释放鼠标然后它将不再跟随鼠标。
这是我必须向屏幕添加球的代码,所以如果可以只调整代码就会很棒。它分为3个类
import java.awt.BorderLayout;
import java.awt.event.*;
import java.util.Random;
import javax.swing.*;
public class DrawBalls {
JFrame frame = new JFrame();
final DrawPanel drawPanel = new DrawPanel();
JPanel controlPanel = new JPanel();
JButton createBallButton = new JButton("Add ball");
DrawBalls(){
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
controlPanel.add(createBallButton);
frame.add(drawPanel);
frame.add(controlPanel, BorderLayout.SOUTH);
frame.pack();
frame.setVisible(true);
{
drawPanel.addMouseMotionListener(new MouseMotionAdapter() {
@Override
public void mouseMoved(MouseEvent e) {
super.mouseMoved(e);
for (Ball b : drawPanel.getBalls()) {
if (b.getBounds().contains(me.getPoint())) {
//this has it being the same coordinates as the mouse i don't know
//how to have it run constantly so when i move it, it doesn't work
b.setx(me.getX()-(b.radius/2));
b.sety( me.getY()-(b.radius/2));
drawPanel.repaint();
}
}
}
});
createBallButton.addActionListener(new ActionListener() {
Random rand = new Random();
private int counter = 1;
int noOfClicks = 1;
public void actionPerformed(ActionEvent e) {
if(noOfClicks<=10){
int ballRadius = 10;
int x = rand.nextInt(drawPanel.getWidth());
int y = rand.nextInt(drawPanel.getHeight());
//check that we dont go offscreen by subtarcting its radius unless its x and y are not bigger than radius
if (y > ballRadius) {
y -= ballRadius;
}
if (x > ballRadius) {
x -= ballRadius;
}
drawPanel.addBall(new Ball(x, y, ballRadius, counter));//add ball to panel to be drawn
counter++;//increase the ball number
noOfClicks++;
}
}
});
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
@Override
public void run() {
new DrawBalls();
}
});
}
球类
import java.awt.*;
import java.awt.geom.*;
public class Ball {
private Color color;
private int x, y;
private int radius;
private final int number;
Ball(int x, int y, int radius, int counter) {
this.x = x;
this.y = y;
this.radius = radius;
this.number = counter;
this.color = Color.RED;
}
public void draw(Graphics2D g2d) {
Color prevColor = g2d.getColor();
g2d.drawString(number + "", x + radius, y + radius);
g2d.setColor(color);
g2d.fillOval(x, y, radius, radius);
g2d.setColor(prevColor);
}
public Rectangle2D getBounds() {
return new Rectangle2D.Double(x, y, radius, radius);
}
int getNumber() {
return number;
}
}
DrawPanel
import java.awt.*;
import java.util.*;
import javax.swing.*;
public class DrawPanel extends JPanel {
ArrayList<Ball> balls = new ArrayList<Ball>();
public void addBall(Ball b) {
balls.add(b);
repaint();
}
public ArrayList<Ball> getBalls() {
return balls;
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g;
for (Ball ball : balls) {
ball.draw(g2d);
}
}
@Override
public Dimension getPreferredSize() {
return new Dimension(300, 300);
}
}
答案 0 :(得分:2)
一种方法是使您的Ball类成为实际的Swing组件。然后你可以使用ComponentMover类。
编辑:
如何将课程变成一个摇摆组件
基本上,您将draw(...)代码移动到JComponent的paintComponent()方法中。这是一个简单的示例,可以为您完成所有自定义绘制,因为绘制基于Shape对象。您仍然需要修改代码以绘制“数字”。
import java.awt.*;
import java.awt.event.*;
import java.awt.geom.*;
import javax.swing.*;
public class ShapeComponent extends JComponent
{
Shape shape;
public ShapeComponent(Shape shape)
{
this.shape = shape;
setOpaque( false );
}
public Dimension getPreferredSize()
{
Rectangle bounds = shape.getBounds();
return new Dimension(bounds.width, bounds.height);
}
@Override
protected void paintComponent(Graphics g)
{
super.paintComponent(g);
Graphics2D g2d = (Graphics2D)g;
g2d.setColor( getForeground() );
g2d.fill( shape );
}
@Override
public boolean contains(int x, int y)
{
return shape.contains(x, y);
}
private static void createAndShowUI()
{
ShapeComponent ball = new ShapeComponent( new Ellipse2D.Double(0, 0, 50, 50) );
ball.setForeground(Color.GREEN);
ball.setSize( ball.getPreferredSize() );
ball.setLocation(10, 10);
ShapeComponent square = new ShapeComponent( new Rectangle(30, 30) );
square.setForeground(Color.ORANGE);
square.setSize( square.getPreferredSize() );
square.setLocation(50, 50);
JFrame frame = new JFrame();
frame.setLayout(null);
frame.add(ball);
frame.add(square);
frame.setSize(200, 200);
frame.setVisible(true);
MouseListener ml = new MouseAdapter()
{
public void mouseClicked( MouseEvent e )
{
System.out.println( "clicked " );
}
};
ball.addMouseListener( ml );
square.addMouseListener( ml );
}
public static void main(String[] args)
{
EventQueue.invokeLater(new Runnable()
{
public void run()
{
createAndShowUI();
}
});
}
}
这种方法与trashgod使用Icon的建议之间的主要区别在于鼠标事件仅在鼠标悬停在球上时生成,而不是球的矩形角,因为contains(...)
方法尊重形状你画的是什么。