📄 solarsystem.java
字号:
// ///////////////////////////////////////////////
//
// Solarsystem.java
//
// 开发者:薛卫东
// ///////////////////////////////////////////////
// 简介:
// 太阳系行星运行图
// ///////////////////////////////////////////////
import java.awt.*;
import java.awt.event.*;
import java.awt.image.BufferedImage;
import java.io.File;
import java.util.Date;
import javax.imageio.ImageIO;
import javax.swing.*;
class J_Panel extends JPanel implements ActionListener
{
BufferedImage m_image = new BufferedImage(1300,800,BufferedImage.TYPE_INT_RGB);//缓存帧,用于提高动画质量
BufferedImage sun , mercury , venus , earth , mars , jupiter , saturn , uranus , neptune , pluto;//太阳系成员
Timer m_timer; //通过计时器控制动画
public static int i,j; //记录鼠标操作与绘图原点之间的距离,以便实现图像拖拽功能
public static int n=0; //记录鼠标滚轮旋转格数,以便实现图像缩放功能
public static int jishu=1; //计数,用于鼠标双击事件(停止和启动动画)
static int O_x = 600;
static int O_y = 375; //画图原点
static long timer1=0 , timer2=0; //记录鼠标点击时的当前时间,用于通过时间监视实现鼠标双击
double t1=0 , t2=0 , t3=0 , t4=0 , t5=0 , t6=0 , t7=0 , t8=0 , t9=0;
//行星运行时变换的角度,依次对应:水星、金星、地球、火星、木星、土星、天王星、海王星、冥王星
boolean m_frozen = false; //计时器状态,当为true时暂停动画;否则启动
boolean m_ready = true; //缓存帧准备状态,用于提高动画质量
public J_Panel()
{
//异常处理开始
try
{
//读取照片,依次对应:水星、金星、地球、火星、木星、土星、天王星、海王星、冥王星
File f1 = new File("sun.gif");
File f2 = new File("mercury.gif");
File f3 = new File("venus.gif");
File f4 = new File("earth.gif");
File f5 = new File("mars.gif");
File f6 = new File("jupiter.gif");
File f7 = new File("saturn.gif");
File f8 = new File("uranus.gif");
File f9 = new File("neptune.gif");
File f10 = new File("pluto.gif");
sun = ImageIO.read(f1);
mercury = ImageIO.read(f2);
venus = ImageIO.read(f3);
earth = ImageIO.read(f4);
mars = ImageIO.read(f5);
jupiter = ImageIO.read(f6);
saturn = ImageIO.read(f7);
uranus = ImageIO.read(f8);
neptune = ImageIO.read(f9);
pluto = ImageIO.read(f10);
m_timer = new Timer(50,this);
m_timer.setInitialDelay(0);
m_timer.setCoalesce(true);
m_timer.start(); //设置计时器参数,控制动画效果(每隔50毫秒显示一帧动画)
this.addMouseListener(new MouseAdapter()
{
public void mousePressed(MouseEvent e)
{
i=e.getX()-O_x;
j=e.getY()-O_y;
}
});//鼠标点击控制移动距离
this.addMouseListener(new MouseAdapter()
{
public void mousePressed(MouseEvent e)
{
if(jishu==1)
{
jishu=2;
Date d1 = new Date();
timer1 = d1.getTime();
}//得到双击事件中第一次点击时的当前时间与1970年1月1日格林威治标准时间00:00:00之差的毫秒数
else if(jishu==2)
{
jishu=1;
Date d2 = new Date();
timer2 = d2.getTime();
}//得到双击事件中第二次点击时的当前时间与1970年1月1日格林威治标准时间00:00:00之差的毫秒数
if(Math.abs(timer2-timer1)<=400)
{
m_frozen = !m_frozen;
if(m_frozen)
m_timer.stop();
else m_timer.start();
}//设定双击时间间隔(400毫秒以内),用以判断是否为双击事件,进而引发动画停止与启动
}
});//鼠标双击控制动画停止或启动
this.addMouseMotionListener(new MouseMotionAdapter()
{
public void mouseDragged(MouseEvent e)
{
O_x=e.getX()-i;
O_y=e.getY()-j;
repaint(); //调用paint()方法
}
});//注册鼠标拖动事件,实现图像拖拽功能
this.addMouseWheelListener(new MouseAdapter()
{
public void mouseWheelMoved(MouseWheelEvent e)
{
n+=e.getWheelRotation();//记录鼠标滚轮旋转格数,以便实现图像缩放功能
}
});//注册鼠标滚轮事件,实现图像缩放功能
}
catch (Exception e)
{
System.err.println("发生异常:"+e);
e.printStackTrace();
}
//异常处理结束
}//J_Panel构造方法结束
//配合计时器每隔50毫秒触发事件(此中为显示一帧动画)
public void actionPerformed(ActionEvent e)
{
//按实际比例比较精确地计算各行星运行时坐标变换(通过角度变换实现)
t1+=0.333333*100*Math.PI/180; //水星运行时角度变换
t2+=0.1825*100*Math.PI/180; //金星运行时角度变换
t3+=0.125*100*Math.PI/180; //地球运行时角度变换
t4+=0.071*100*Math.PI/180; //火星运行时角度变换
t5+=0.026*125*Math.PI/180; //木星运行时角度变换
t6+=0.011*125*Math.PI/180; //土星运行时角度变换
t7+=0.00374*150*Math.PI/180; //天王星运行时角度变换
t8+=0.00198*150*Math.PI/180; //海王星运行时角度变换
t9+=0.0017*250*Math.PI/360; //冥王星运行时角度变换
repaint(); //调用paint()方法,实现动画效果
}
//
public void mb_draw()
{
if(!m_ready) return;
m_ready = false; //开始准备缓存帧
Graphics2D g2d = m_image.createGraphics();
g2d.clearRect(0,0,getWidth(),getHeight());//清屏,以实现动画效果
g2d.setColor(Color.black);
g2d.fillRect(0,0,1300,900);//背景
g2d.drawImage(sun,O_x-25-n,O_y-25-n,50+2*n,50+2*n,this);//太阳
g2d.translate(O_x,O_y);//原点移动到太阳中心
g2d.rotate(-0.1521730476);//水星轨道倾角(7.0度)
//绘制水星轨道
g2d.setColor(Color.blue);
g2d.drawArc((int)(-30-6*n/5),(int)(-8-8*n/25),(int)(60+12*n/5),(int)(16+16*n/25),30,180);
g2d.setColor(Color.green);
g2d.drawArc((int)(-30-6*n/5),(int)(-8-8*n/25),(int)(60+12*n/5),(int)(16+16*n/25),210,180);
//通过坐标变化绘制水星,实现水星按轨道旋转(通过角度变化实现)
g2d.drawImage(mercury,(int)((30+6*n/5)*Math.cos(t1)-5-n/5),
(int)((8+8*n/25)*Math.sin(t1)-5-n/5),(int)(10+2*n/5),(int)(10+2*n/5),this);
g2d.rotate(+0.1521730476);
//水星系统结束
g2d.rotate(-0.08934119457);//金星轨道倾角(3.4度)
//绘制金星轨道
g2d.setColor(Color.blue);
g2d.drawArc((int)(-40-8*n/5),(int)(-12-12*n/25),(int)(80+16*n/5),(int)(24+24*n/25),30,180);
g2d.setColor(Color.green);
g2d.drawArc((int)(-40-8*n/5),(int)(-12-12*n/25),(int)(80+16*n/5),(int)(24+24*n/25),210,180);
//通过坐标变化绘制金星,实现金星按轨道旋转(通过角度变化实现)
g2d.drawImage(venus,(int)((40+8*n/5)*Math.cos(t2)-8-8*n/25),
(int)((12+12*n/25)*Math.sin(t2)-8-8*n/25),(int)(16+16*n/25),(int)(16+16*n/25),this);
g2d.rotate(+0.08934119457);
//金星系统结束
//绘制地球轨道
g2d.setColor(Color.blue);
g2d.drawArc((int)(-50-2*n),(int)(-20-4*n/5),(int)(100+4*n),(int)(40+8*n/5),30,180);
g2d.setColor(Color.green);
g2d.drawArc((int)(-50-2*n),(int)(-20-4*n/5),(int)(100+4*n),(int)(40+8*n/5),210,180);
//通过坐标变化绘制地球,实现地球按轨道旋转(通过角度变化实现)
g2d.drawImage(earth,(int)((50+2*n)*Math.cos(t3)-8-8*n/25),
(int)((20+4*n/5)*Math.sin(t3)-8-8*n/25),(int)(16+16*n/25),(int)(16+16*n/25),this);
//地球系统结束(无倾角)
g2d.rotate(-0.03141592654);//火星轨道倾角(1.8度)
//绘制火星轨道
g2d.setColor(Color.blue);
g2d.drawArc((int)(-70-14*n/5),(int)(-25-n),(int)(140+28*n/5),(int)(50+2*n),30,180);
g2d.setColor(Color.green);
g2d.drawArc((int)(-70-14*n/5),(int)(-25-n),(int)(140+28*n/5),(int)(50+2*n),210,180);
//通过坐标变化绘制火星,实现火星按轨道旋转(通过角度变化实现)
g2d.drawImage(mars,(int)((70+14*n/5)*Math.cos(t4)-8-8*n/25),
(int)((25+n)*Math.sin(t4)-8-8*n/25),(int)(16+16*n/25),(int)(16+16*n/25),this);
g2d.rotate(+0.03141592654);
//火星系统结束
g2d.rotate(-0.02268928028);//木星轨道倾角(1.3度)
//绘制木星轨道
g2d.setColor(Color.blue);
g2d.drawArc((int)(-105-21*n/5),(int)(-30-6*n/5),(int)(210+42*n/5),(int)(60+12*n/5),30,180);
g2d.setColor(Color.green);
g2d.drawArc((int)(-105-21*n/5),(int)(-30-6*n/5),(int)(210+42*n/5),(int)(60+12*n/5),210,180);
//通过坐标变化绘制木星,实现木星按轨道旋转(通过角度变化实现)
g2d.drawImage(jupiter,(int)((105+21*n/5)*Math.cos(t5)-25-n),
(int)((30+6*n/5)*Math.sin(t5))-25-n,50+2*n,50+2*n,this);
g2d.rotate(+0.02268928028);
//木星系统结束
g2d.rotate(-0.0736332313);//土星轨道倾角(2.5度)
//绘制土星轨道
g2d.setColor(Color.blue);
g2d.drawArc((int)(-190-38*n/5),(int)(-50-2*n),(int)(380+76*n/5),100+4*n,30,180);
g2d.setColor(Color.green);
g2d.drawArc((int)(-190-38*n/5),(int)(-50-2*n),(int)(380+76*n/5),100+4*n,210,180);
//通过坐标变化绘制土星,实现土星按轨道旋转(通过角度变化实现)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -