我现在正在做一个3体模拟(重力),我通过随机猜测dt(时间步长)并把它们放入一个迭代方程中,计算出每一个新的x和y值。然后在每次迭代之后,我将每个x和y值保存在一个arraylist中,它包含了我放入变量的时间dt。我对java非常陌生,我很感激每一个答案,尽管考虑到我的知识,我会更感谢一个更简单的答案(我是一个16岁的非英语国家,我为任何错误道歉)我已经导入了arraylist,list和linkedlist,我的x和y列表的一个例子是
List<Double> xlistobject1 = new ArrayList<Double>();
List<Double> ylistobject1 = new ArrayList<Double>();
在while循环迭代过程中:
xlistobject1.add(xobject1); // where xobject1 and yobject1 are the x and y
ylistobject1.add(yobject1); // coordinates
我已经研究了最好的方法来制作动画,但是没有一个适合我。我真的不能把我的头围绕画布,jframe等等,因为他们需要这么多的先验知识,这个主题。由于时间跨度已经由n个迭代次数dt来定义,我想你不能在列表中的每个位置都画一个点然后按play,因为要创建一个相对平滑的动画,你必须带一个计时器来设置一个固定的动画长度,比如30秒,这意味着你将时间重新缩放到这个固定的长度上,最终会丢失精确的坐标信息,因为我的显示器只能显示1920x1080像素?
我已经得到了:
我复制了eclipse安装中唯一的一个框架(在文本的底部),并删除了移动部分,该部分已经存在,试图移动到列表中循环的x和y的值,直到我的列表被清除为止。在那之后,我会重新调整模拟的时间(n-counterdt),这样它可以适应20秒,每秒30帧,这样模拟有600个时间步,所以如果我没有出错,你必须除以(n-counter*dt)/600来得到x和y比例因子。我的主要问题是如何将我的想法实现到java中。我希望我没把你搞糊涂,也没说废话。谢谢你的帮助!:)这是我的“动画”-代码:
import java.util.ArrayList;
import java.util.List;
import java.util.LinkedList;
import java.util.Vector;
import java.util.Stack;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Graphics;
import javax.swing.JFrame;
import javax.swing.JPanel;
final public class Test
{
JFrame frame;
DrawPanel drawPanel;
private int oneX = 7;
private int oneY = 7;
public static void main(String... args)
{
new Test().go();
}
private void go()
{
frame = new JFrame("Test");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
drawPanel = new DrawPanel();
frame.getContentPane().add(BorderLayout.CENTER, drawPanel);
frame.setResizable(false);
frame.setSize(1920, 1000);
frame.setLocationByPlatform(true);
frame.setVisible(true);
moveIt();
}
class DrawPanel extends JPanel
{
private static final long serialVersionUID = 1L;
public void paintComponent(Graphics g)
{
g.setColor(Color.BLUE);
g.fillRect(0, 0, this.getWidth(), this.getHeight());
g.setColor(Color.RED);
g.fillRect(3, 3, this.getWidth() - 6, this.getHeight() - 6);
g.setColor(Color.WHITE);
g.fillRect(6, 6, this.getWidth() - 12, this.getHeight() - 12);
g.setColor(Color.BLACK);
g.fillRect(oneX, oneY, 6, 6);
// Object 1
! for i = 0 to xlistobject1.count - 1
! //move circle to x=xlistobject1.item(i)
! //move circle to y=ylistobject1.item(i)
next
try
{
Thread.sleep(10);
}
catch (Exception e)
{
e.printStackTrace();
}
frame.repaint();
}
}
}
1条答案
按热度按时间9rbhqvlz1#
重要的是要了解
paintComponent
方法只是按组件在某个时刻出现的样子绘制组件——它不是一个进行动画的地方。我对你的代码做了两个小改动,让你明白这一点:
把循环和睡眠从
paintComponent
.添加了一个计时器
oneX
以及oneY
并触发你的DrawPanel
.你会想做更复杂的x和y坐标更新,你会想画更多的东西
paintComponent
,但我希望这能让你开始。以后要考虑的另一个技巧是:为要显示的每个对象创建一个类,并拥有该类的示例列表,而不是为对象的每个属性创建单独的列表。这样,在创建新对象时只有一个插入操作,一个
get
从列表中可以获得绘制或更新它所需的所有属性。