简体   繁体   English

如何制作动画圈?

[英]How to make an animated circle?

Im still learning GUI, still having some trouble getting my head around threads :/ 我仍在学习GUI,但仍然难以理解线程:/

Im making this GUI in which there are 2 circles, one big (100x100) and one small (50x50). 我在制作这个有2个圆圈的GUI,一个大(100x100)和一个小(50x50)。 The small one will go to the edge of the big circle and during 0.5seconds, the small circle will go to the center and that it when the user has to click. 小圆圈将移到大圆圈的边缘,在0.5秒内,小圆圈将移至中心,当用户必须单击时将移至小圆圈。 Whenever the user clicks when the circle is in the middle then the user scores. 每当用户单击圆圈中间的位置时,用户就会得分。 The only trouble im having is that the circle is not moving about as I suspect its something got to do with my threads, hence the reason why im using threads, to get to know how to use them. 我唯一遇到的麻烦是该圆环并没有移动,因为我怀疑它与我的线程有关,因此,我使用线程来了解如何使用它们的原因。

GUI GUI

public class gui extends JPanel implements MouseListener,
    Runnable {
Thread t = new Thread();


int score = 0;
int rnd;
static final int smallcircleposx = 75;
static final int smallcircleposy = 75;
int circleposx = 75;
int circleposy = 75;
int mousex, mousey;
Random random = new Random();

public gui() {

}

public void paintComponent(Graphics g) {
    super.paintComponent(g);
    g.setColor(Color.BLUE);
    g.fillOval(50, 50, 100, 100);
    g.setColor(Color.RED);
    g.fillOval(circleposx, circleposy, 50, 50);

}

// THREAD FOR MOVING THE CIRCLE
public void run() {
    rnd = random.nextInt(999);

    if (rnd % 5 == 0) {
        circleposx = circleposx + 25;
    } else if (rnd % 4 == 0) {
        circleposx = circleposx - 25;
    } else if (rnd % 3 == 0) {
        circleposy = circleposy + 25;
    } else {
        circleposy = circleposy - 25;
    }

    try {
        Thread.sleep(500);
        circleposx = smallcircleposx;
        circleposy = smallcircleposy;
    } catch (InterruptedException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }

}

public void mouseClicked(MouseEvent m) {

    if (circleposx == smallcircleposx && circleposy == smallcircleposy) {
        score++;
    }
}

MAIN 主要

public class main {

public static void main(String[] args) {
    JFrame frame = new JFrame("Circle enlarger");
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    frame.setSize(400,400);
    frame.setVisible(true);

    gui co = new gui();
    frame.add(co);
    frame.addMouseListener(co);
    Thread x = new Thread(new gui());
    x.start();


}

}

I am aware that I haven't used all the mouselistener methods. 我知道我没有使用所有的mouselistener方法。

Some points to remember: 需要记住的几点:

  1. Use MouseAdaptor instead of MouseListener if you are not overriding all the methods. 如果不覆盖所有方法,请使用MouseAdaptor而不是MouseListener

  2. Don't paint directly over top level container such as JFrame , JApplet instead use JPanel 不要直接在顶级容器(例如JFrame绘制,而是使用JPanel绘制JApplet

  3. Don't use Thread.sleep() that sometime hangs the whole swing application instead try with Swing Timer that is most suitable for swing application. 不要使用有时会挂起整个Swing应用程序的Thread.sleep() ,而是尝试最适合Swing应用程序的Swing Timer

    Read more How to Use Swing Timers 了解更多如何使用Swing计时器

  4. Don't forget to call super.paintComponent() in overridden paintComponent() method. 不要忘记在重写的paintComponent()方法中调用super.paintComponent()

  5. Call frame.setVisible(true) in the end after adding all the components. 添加所有组件后,最后调用frame.setVisible(true)

  6. Use frame.pack() instead of frame.setSize() that fits the components as per component's preferred size. 使用frame.pack()代替根据组件的首选大小适合组件的frame.setSize()

  7. Override getPreferredSize() to set the preferred size of the JPanel in case of custom painting. 重写getPreferredSize()以在自定义绘制的情况下设置JPanel的首选大小。

  8. Use SwingUtilities.invokeLater() or EventQueue.invokeLater() to make sure that EDT is initialized properly. 使用SwingUtilities.invokeLater()EventQueue.invokeLater()确保EDT正确初始化。

    Read more 阅读更多

It's worth reading Lesson: Performing Custom Painting 值得一读的课:执行自定义绘画


Sample code: ( change it as per your custom painting ) 示例代码:( 根据您的自定义绘画进行更改

private Timer timer;
...
// 500 Milli-seconds 
timer = new javax.swing.Timer(500, new ActionListener() {

    @Override
    public void actionPerformed(ActionEvent arg0) {
        // change the coordinate
        panel.repaint();

        if (condition) {
            timer.stop(); // you can stop the timer anytime
        }
    }
});
timer.setRepeats(true); // you can turn-off the repeatation
timer.start();

public static void main(String args[]) {
    SwingUtilities.invokeLater(new Runnable() {

        @Override
        public void run() {
            // Initialize the UI
        }
    });
}

class MyJPanel extends JPanel {
    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        ...
    }

    @Override
    public Dimension getPreferredSize() {
        return new Dimension(..., ...);
    }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM