Java 窗口 绘制图形 #3
阅读原文时间:2023年07月09日阅读:1

写在前面:

  高数下学到第二章,突发奇想要写一个程序画二元函数图像

  思路分了三层:

  ①抽象层:

    因变量z,自变量x、y,坐标原点x0、y0、z0

  ②投影实现层:

    屏幕投影坐标px、py,x轴与屏幕水平方向夹角theta1,z轴与屏幕铅直方向夹角theta2,缩放变量S

    分两种情况考虑了:

      1)单纯以z轴为旋转轴

        yp=S*z

        xp=S*(-x*sintheta1 + y*costheta2)

      2)以原点为定点旋转

        yp=S*(z*costheta2-x*sintheta2+y*costheta2) 这个经检验是错的

        xp=S*(-x*sintheta1 + y*costheta2)

  ③操作层:演草纸上写的和实际程序写的不一样,略

  运行效果:

  可以缩放、平移,但目前只能做到绕y轴旋转(因为绕原点旋转的代码挂了)

  pong友建议用矩阵做投影变换,有空试试

代码如下:

1 package my_package;
2
3 import java.awt.*;
4 import java.awt.event.MouseAdapter;
5 import java.awt.event.MouseEvent;
6 import java.awt.event.MouseMotionAdapter;
7 import java.awt.event.MouseWheelEvent;
8 import java.awt.event.MouseWheelListener;
9 import java.io.*;
10 import javax.swing.JFrame;
11 import javax.swing.JPanel;
12
13 public class PonysAlgorithm2 extends JFrame
14 {
15 private static final long serialVersionUID = 1L;
16 static int pony_winx=800,pony_winy=600;//窗口的长和宽
17 static int pony_scale=2,pony_scale_tmp=4;//视图缩放变量
18 static int theta1=0,theta2=0;//水平旋转角度,铅直旋转角度
19 static int pony_square=250;//绘制xy正方形区域趋边长的一半
20 static int pony_px=pony_winx/2,pony_py=pony_winy/2;//屏幕投影变量px和py
21
22 static int pony_framex_ori,pony_framey_ori;//鼠标移动辅助变量
23 static int pony_theta1_tmp,pony_theta2_tmp;//角度随鼠标移动变化辅助变量
24 static int pony_px_tmp,pony_py_tmp;//屏幕投影量随鼠标移动变化辅助变量
25 static int pony_project_x_tmp,pony_project_y_tmp;//屏幕投影量计算辅助变量
26 static float pony_precision=40.0f;//绘制精度,但绘制点数只受pony_square影响,不受精度影响
27
28 static double pony_project_x(double x, double y){//计算在屏幕上的投影px
29 return (y*Math.cos(theta1/180.0f)-x*Math.sin(theta1/180.0f))*pony_scale;
30 }
31 static double pony_project_y(double z, double x, double y){//计算在屏幕上的投影py
32 return z*pony_scale;
33 }
34 static double pony_z(double x, double y){//计算函数值
35 return x*x/4-y*y/9;
36 }
37
38 public static void main(String[] args) throws Exception
39 {
40 JFrame ponyFrame=new JFrame("Pony's Algorithm II");
41 ponyFrame.setLayout(null);
42 JPanel ponyJPanel=new JPanel(){
43 private static final long serialVersionUID = 1L;
44 public void paint(Graphics g){
45 super.paint(g);
46 for(int y=-pony_square;y<=pony_square;++y) 47 { 48 g.setColor(Color.getHSBColor(0.54f+0.2f*(y+pony_square)/(pony_square*2.0f), 1.0f, 1.0f)); 49 for(int x=-pony_square;x<=pony_square;++x) 50 { 51 pony_project_x_tmp=pony_px+(int)pony_project_x(x/pony_precision,y/pony_precision); 52 pony_project_y_tmp=pony_py+(int)pony_project_y(pony_z(x/pony_precision,y/pony_precision),x/pony_precision,y/pony_precision); 53 g.drawLine(pony_project_x_tmp, pony_project_y_tmp, pony_project_x_tmp, pony_project_y_tmp); 54 } 55 } 56 } 57 }; 58 59 /*Whole*/ 60 ponyFrame.setSize(pony_winx,pony_winy); 61 ponyFrame.setResizable(false); 62 ponyFrame.setLocationRelativeTo(null); 63 ponyFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 64 65 /*ICON*/ 66 File directory = new File(""); 67 ponyFrame.setIconImage(Toolkit.getDefaultToolkit().getImage(directory.getCanonicalPath()+"\\icons\\2.png")); 68 69 /*DRAW*/ 70 ponyJPanel.setBounds(0, 0, pony_winx, pony_winy); 71 ponyFrame.add(ponyJPanel); 72 73 /*MOUSE*/ 74 ponyFrame.addMouseListener(new MouseAdapter() { 75 @Override 76 public void mousePressed(MouseEvent e) {//当任意鼠标键按下时,记录变量 77 pony_framex_ori=e.getXOnScreen(); 78 pony_framey_ori=e.getYOnScreen(); 79 pony_theta1_tmp=theta1; 80 pony_theta2_tmp=theta2; 81 pony_px_tmp=pony_px; 82 pony_py_tmp=pony_py; 83 } 84 }); 85 ponyFrame.addMouseMotionListener(new MouseMotionAdapter() {//当鼠标键按下并移动时,记录变量 86 @Override 87 public void mouseDragged(MouseEvent e) {//两个角度的改变 88 if(e.isShiftDown() && e.getButton()==0){ 89 theta1=pony_theta1_tmp-(e.getXOnScreen()-pony_framex_ori)/2; 90 theta2=pony_theta2_tmp+(e.getYOnScreen()-pony_framey_ori)/2; 91 } 92 else if(e.getButton()==0){//两个投影坐标的改变 93 pony_px=pony_px_tmp+(e.getXOnScreen()-pony_framex_ori)/1; 94 pony_py=pony_py_tmp+(e.getYOnScreen()-pony_framey_ori)/1; 95 } 96 ponyJPanel.repaint(); 97 } 98 }); 99 ponyFrame.addMouseWheelListener(new MouseWheelListener() {//鼠标滚轮滚动时,对图像进行缩放 100 @Override 101 public void mouseWheelMoved(MouseWheelEvent e) { 102 if(e.getWheelRotation()==1) { 103 if(pony_scale_tmp>2) {
104 pony_scale_tmp-=1;
105 pony_scale=pony_scale_tmp/2;
106 ponyJPanel.repaint();
107 }
108 }
109 if(e.getWheelRotation()==-1) {
110 pony_scale_tmp+=1;
111 pony_scale=pony_scale_tmp/2;
112 ponyJPanel.repaint();
113 }
114 }
115 });
116
117 ponyFrame.setVisible(true);
118 return;
119 }
120 }

  十分良心加了注释哈哈

附件:

*jar所在目录*\\icons\\

2.png

手机扫一扫

移动阅读更方便

阿里云服务器
腾讯云服务器
七牛云服务器