Слушатель действия таймера Java

1

может использовать вашу домашнюю домашнюю работу с участием таймеров качания, слушателей действий и нескольких объектов. Я не знаю, разрешена ли публикация вопроса, но у меня проблемы с анимацией, вот что я до сих пор

Создайте класс Particle, который имеет два двойных поля x и y, конструктор, который инициализирует эти поля случайными значениями от 0 до 500, методы getX и getY, которые возвращают свои значения, и метод void move(), который случайным образом добавляет или вычитает один из каждое из значений x и y. (Величины, добавленные к x и y, представляют собой два отдельных случайных числа.) Затем создайте класс ParticleFieldWithTimer, который расширяет JPanel. Этот класс должен быть размером 500 * 500 пикселей. Его конструктор должен сначала заполнить поле ArrayList 100 объектами частиц, а затем запустить таймер Swing, который гасит 25 раз в секунду. При каждом тике слушатель действия должен сначала вызвать метод перемещения для каждой частицы, а затем вызвать перерисовку. Метод paintComponent ParticleFieldWithTimer должен рисовать каждую частицу в виде прямоугольника 3 * 3 в ее текущие координаты. Убедитесь, что таймер остановится, когда пользователь закрывает рамку

Это класс ParticleFieldWithTimer

import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.util.ArrayList;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.Timer;


public class ParticleFieldWithTimer extends JPanel{
    private ArrayList<Particle> particle = new ArrayList<Particle>();
    Timer timer; 
    boolean b; 
    public ParticleFieldWithTimer (){
        this.setPreferredSize(new Dimension(500,500));


    for(int i = 0; i < 100; i++) { 
        particle.add(new Particle());
        timer = new Timer(40, new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent ae) {
                // change polygon data
                // ...
                Particle p = new Particle();
                p.move();
                repaint();

            }
        });


    }





}
   public void paintComponent(Graphics g) {
        super.paintComponent(g);
        Graphics2D g2 = (Graphics2D)g;
        for (Particle p: particle) {

        double temp1 = p.getX();
        double temp2 = p.getX();
        int tempX = (int) temp1;
        int tempY = (int) temp2;
        g2.fillRect(tempX, tempY, 3, 3);
        }




    }
   public static void main(String[] args) {
        final JFrame f = new JFrame("ParticleField");
        final ParticleFieldWithTimer bb = new ParticleFieldWithTimer();
        f.setLayout(new FlowLayout());
        f.add(bb);
        f.addWindowListener(new WindowAdapter() {
            public void windowClosing(WindowEvent we) {
                try {
                    bb.finalize();
                } catch (Throwable e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
                f.dispose();
            }
        });
        f.pack();
        f.setVisible(true);
    }
}

Это класс частиц

import java.util.Random;


public class Particle {
private double x , y ;

Random r = new Random();
public Particle () {

    x = r.nextDouble()*500;
    y = r.nextDouble()*500;

}
public Double getX() {
    return x;
}
public Double getY() {
    return y;
}
public void move() {

    x = r.nextInt(2) - 1;
    y = r.nextInt(2) - 1;
    System.out.println(x + "  " + y);
}

}

Теги:
timer
swing
paintcomponent

1 ответ

4
Лучший ответ

Эта...

for(int i = 0; i < 100; i++) { 
    particle.add(new Particle());
    timer = new Timer(40, new ActionListener() {
        @Override
        public void actionPerformed(ActionEvent ae) {
            // change polygon data
            // ...
            Particle p = new Particle();
            p.move();
            repaint();

        }
    });
}

Это неправильный подход, он создает 100 Timer, что повлияет на производительность вашей системы.

Вы также создаете новый Particle каждый раз, когда таймер тикает, что не то, что вы действительно хотите сделать, вы хотите повлиять на Particle вы уже создали...

Вместо этого создайте свои частицы...

for(int i = 0; i < 100; i++) { 
    particle.add(new Particle());
}

Затем создайте свой Timer и внутри него, прорежьте частицы, которые вы уже создали...

timer = new Timer(40, new ActionListener() {
    @Override
    public void actionPerformed(ActionEvent ae) {
        for (Particle p : particle) {
            p.move();
        }
        repaint();
    }
});

Не забудьте запустить таймер...

timer.start();

Или измените цвет контекста Graphics, который, вероятно, все еще установлен на фоне панели...

Graphics2D g2 = (Graphics2D) g;
g2.setColor(Color.RED);
for (Particle p : particle) {

Я также отметил, что...

x = r.nextInt(2) - 1;
y = r.nextInt(2) - 1;

Не делает то, что вы хотите. Он всегда будет делать значения между -1 и 1. Вместо этого вы хотите добавить результат к значениям x/y...

x += r.nextInt(2) - 1;
y += r.nextInt(2) - 1;

Теперь этот тип сделал значения "перетаскиванием" по экрану (в основном) единообразным образом...

Вы можете попробовать использовать...

x += r.nextBoolean() ? 1 : - 1;
y += r.nextBoolean() ? 1 : - 1;

Но это в конечном итоге заставило их танцевать на месте (в основном)...

  • 0
    Привет, спасибо за ответ. Разве перекраска не должна быть внутри цикла for и какие изменения я должен внести в компонент paint?
  • 0
    Нет, вы хотите обновить всю модель, а затем сделать один repaint . На самом деле это не имеет большого значения, так как RepaintManager может объединять повторяющиеся вызовы для repaint в одно событие рисования, но зачем рисковать. Обновите модель в один шаг, обновите вид в следующий. Поскольку действие actionPerformed выполняется в контексте EDT, вызов repaint будет иметь никакого эффекта, пока ПОСЛЕ того, actionPerformed метод actionPerformed любом случае actionPerformed ( paintComponent не может быть вызван, пока actionPerformed существует actionPerformed )
Показать ещё 6 комментариев

Ещё вопросы

Сообщество Overcoder
Наверх
Меню