JAVA时钟
2015-11-12 12:39
495 查看
import java.awt.Color; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.Insets; import java.awt.RenderingHints; import java.awt.Shape; import java.awt.geom.Ellipse2D; import java.awt.geom.GeneralPath; import java.awt.geom.Line2D; import java.awt.geom.Rectangle2D; import java.util.Calendar; import java.util.Date; import javax.swing.JFrame; import javax.swing.JPanel; import javax.swing.UIManager; /** * 画我的钟表 * * @author Eiffel * */ public class MyClock extends JFrame { MyPanel mp = null; public MyClock() { // 创建我的面板 mp = new MyPanel(); // 添加线程 Thread t = new Thread(mp); t.start(); // 设置窗体属性 this.add(mp); this.setTitle("时钟"); this.setBounds(500, 150, 400, 300); this.setResizable(false); this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); this.setVisible(true); } public static void main(String args[]) { try { UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName()); } catch (Exception e) { e.printStackTrace(); } // 启动程序 new MyClock(); } } class MyPanel extends JPanel implements Runnable { Calendar currentTime = null; //控制点的大小 double s = 0.04; public MyPanel() { // 获取当前时间 currentTime = Calendar.getInstance(); } @Override public void paint(Graphics g) { super.paint(g); Graphics2D g2d = (Graphics2D) g; //画时钟 drawClock(g2d); } // 设置当前Calendar public void setCurrentTime(Date time) { this.currentTime.setTime(time); } // 设置当前Calendar public void setCurrentTime(long millis) { this.currentTime.setTimeInMillis(millis); } // 画出时钟 private void drawClock(Graphics2D g2d) { // 反锯齿开关开,图像变得平滑 g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); Insets insets = getInsets(); // 宽 int wid = getWidth() - insets.left - insets.right; // 高 int hei = getHeight() - insets.top - insets.bottom; // 定义出最长指针(半径)(去除面板的最小边计算)(画出了最大的时钟) //int r = (int) ((Math.min(wid, hei)) / 2 / (1 + s)); int r = (int) ((Math.min(wid, hei)) / 2/(1+s)); // 把绘图平移 g2d.translate(insets.left + r * (1 + s), insets.top + r * (1 + s)); // 将当前 Graphics2D Transform 与缩放转换连接 g2d.scale(1, -1); // 画出60个点 for (int i = 0; i < 60; i++) { // 角度 int angel = 90 - i * 6; double pos[] = operatPos(r, angel); // 画点 paintDot(r, g2d, pos[0], pos[1], i); } // 画秒针 paintSecoundPointer(r, g2d); // 画时针 paintHourPointer(r, g2d); // 画分针 paintMinutePointer(r, g2d); // 画中点 paintCenterPoint(g2d); g2d.translate(-insets.left - r * (1 + s), -insets.top - r * (1 + s)); g2d.scale(1, -1); } // 画秒针 private void paintSecoundPointer(double r, Graphics2D g2d) { g2d.setColor(Color.BLACK); // 获得秒数 int second = currentTime.get(Calendar.SECOND); int angle = 90 - second * 6; double pos[] = operatPos(r * 0.9, angle); double pos1[] = operatPos(r * 0.2, angle + 180); Line2D line = new Line2D.Double(pos1[0], pos1[1], pos[0], pos[1]); g2d.draw(line); // g2d.drawLine((int)pos1[0], (int)pos1[1], (int)pos[0], (int)pos[1]); } // 画时针 private void paintHourPointer(double r, Graphics2D g2d) { // 获得小时时间 int hour = currentTime.get(Calendar.HOUR); // 获得分钟时间 int minute = currentTime.get(Calendar.MINUTE); // 获得秒时间 int second = currentTime.get(Calendar.SECOND); // 计算角度(1小时是30度) double angle = 90 - (hour + minute / 60.0 + second / 3600.0) * 30; // 多边形针(第一个参数确定指针长短,第二个确定指针拐点位置,第三个确定指针尾部的位置) Shape pointerShape = createPointerShape(r * 0.6, r * 0.06, r * 0.1, angle); // double pos[] = operatPos(r, angle); // 画时针 g2d.setColor(Color.LIGHT_GRAY); g2d.fill(pointerShape); // 画时针边框 g2d.setColor(Color.DARK_GRAY); g2d.draw(pointerShape); } // 画分针 private void paintMinutePointer(double r, Graphics2D g2d) { // 获得分钟时间 int minute = currentTime.get(Calendar.MINUTE); // 获得秒时间 int secound = currentTime.get(Calendar.SECOND); // 计算弧度 double angle = 90 - (minute + secound / 60.0) * 6; Shape pointerShape = createPointerShape(r * 0.8, r * 0.04, r * 0.08, angle); g2d.setColor(Color.LIGHT_GRAY); g2d.fill(pointerShape); g2d.setColor(Color.DARK_GRAY); g2d.draw(pointerShape); } /* * 画指针 创建指针路径多变形 * * @param r1 从圆心到指针定点的长度 * * @param r2 从圆心到指针侧边端点的距离 * * @param r3 从圆心到指针尾部端点的距离 * * @param angle 指针角度 * * @return */ private Shape createPointerShape(double r1, double r2, double r3, double angle) { GeneralPath gp = new GeneralPath(); double[] pos = operatPos(r1, angle);// 指针定点 double[] pos1 = operatPos(r2, angle + 90);// 指针侧边断点 gp.append(new Line2D.Double(pos[0], pos[1], pos1[0], pos1[1]), true); double[] pos2 = operatPos(r3, angle + 180);// 指针尾部 gp.lineTo((float) pos2[0], (float) pos2[1]); double[] pos3 = operatPos(r2, angle + 270);// 指针的另一侧边断点(上侧) gp.lineTo((float) pos3[0], (float) pos3[1]); gp.closePath(); return gp; } /* * 画时钟中间那一点 * * @param g2d */ private void paintCenterPoint(Graphics2D g2d) { g2d.setColor(Color.BLUE); // 前两个参数坐标,后两个参数大小 Rectangle2D rect = new Rectangle2D.Double(-2, -2, 6, 6); g2d.fill(rect); } // 画出60个点 private void paintDot(int r, Graphics2D g, double x, double y, int i) { int flag = 0; if (i % 15 == 0) { g.setColor(Color.RED); flag = 2; } else if (i % 5 == 0) { g.setColor(Color.GREEN); flag = 2; } else { g.setColor(Color.BLACK); flag = 1; } if (flag == 2) { // 第一个Ellipse2D 的窗体矩形左上角的 X 坐标,第二个Ellipse2D 的窗体矩形左上角的 Y 坐标 // 第三个参数Eclipse2D总高度,第四个参数总宽度, // 说简单点 前两个表示坐标,后两个表示大小 Ellipse2D rect = new Ellipse2D.Double(x - r * s, y - r * s, r * s * 2, r * s * 2); g.fill(rect); } else if (flag == 1) { Ellipse2D rect = new Ellipse2D.Double(x - r * 0.02, y - r * 0.02, r * 0.04, r * 0.04); g.fill(rect); } } // 计算公式(根据半径和弧长计算坐标) public double[] operatPos(double r, double angle) { // 角度转换成弧度 // System.out.println("角度是:" + angle); double radian = Math.toRadians(angle); // System.out.println("弧度是:" + angle); double x = r * Math.cos(radian); double y = r * Math.sin(radian); // 范围数组 return new double[] { x, y }; } // 执行线程 @Override public void run() { while (true) { try { // 间隔一秒刷新面板 Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } // 重新得到当前的时间,并设置 setCurrentTime(System.currentTimeMillis()); // 重绘 this.repaint(); } } }
相关文章推荐
- jstack命令(Java Stack Trace)
- springsecurity中的配置文件设置remember-me 的原因及其安全性
- Java语法糖
- 曹胜欢,java那些事儿
- Java学习笔记一
- MyEclipse指定源文件夹和编译文件夹的方法
- java和C#的特点
- 90002---POJO和javabean的异同
- java访问权限控制表
- Java类笔试简答
- java类静态域、块,非静态域、块,构造函数的初始化顺序
- 《Java JDK8学习笔记》读书笔记(2)
- 对象的初始化过程
- java 下载邮箱附件到指定目录
- 关于用记事本编写和使用java包
- Struts1和Struts2的区别和对比(完整版)
- Java开发中的23种设计模式详解(转)
- java注解
- 遇到 java.lang.OutOfMemoryError: PermGen space配多少合适我的内存为4G在哪配置Jboss的run.bat还是。。
- Java中普通代码块,构造代码块,静态代码块区别及代码示例