Java绘图——闪烁的天空,炫酷

这里先给出程序的运行效果图
在这里插入图片描述
当然了,程序运行之后是动态的,这里直接截取其中一个状态,有兴趣的道友可以自己运行看看效果~~
在给出程序代码之前,我们先来简单了解下Java绘图相关的一些基本知识。
Java绘图原理

  Java中任何一个可视化图形组件(文本框,标签…)都有一个专门负责显示其界面的函数——paint(Graphics)。
  当可视化组件的界面大小、位置等发生改变时,我们应该重新绘制界面,系统默认repaint() 方法重绘。当需要自己添加代码重绘时,Java也是通过repaint()触发。
  正常情况下,重绘包含两个步骤:

  1. 擦除——update
  2. 绘制——paint
    在重量级组件(AWT)中,重绘时将在repaint()方法中调用update()方法,然后在update()方法中调用paint()方法;对于轻量级组件(Swing),则在repaint()中直接调用paint()方法——注意这里重绘时为了避免闪烁,采用的是双缓冲技术。

在Swing技术中,我们通过repaint()中直接调用paint()方法实现重绘。在绘制过程中也包括几个部分:

  • 绘制组件自身——paintComponent()
  • 绘制边框——paintBorder()
  • 绘制子组件——paintChildren()

我们一般只需要重写paintComponent()函数即可。

双缓冲技术

 双缓冲技术主要是为了解决窗口重绘时出现的闪屏现象:因为重绘有两个步骤——擦除和绘制。那么在连续的重绘时,就会出现中间的一个擦除过程,从而造成闪烁。
 那么采用双缓冲,也就是重绘时,先创建一个和绘图表面(缓冲1)一样大小的内存图片(缓冲2),然后先在内存图片上完成擦除和绘制,最后把缓冲2直接绘制到缓冲1上。
 Swing组件提供了双缓冲的实现功能,而且还可以控制这种功能的开与关。设置方法是setDoubleBuffered(boolean b) ,也可以通过 isDoubleBuffered()方法来检查。
 我们常用的JPanel中间容器默认打开双缓冲,所以我们这个闪烁天空的程序也将借由这个面板来完成。

下面就来说一下这个程序的具体内容:
 程序的功能是在客户区随机显示100个随机大小、随机颜色的*,每100ms刷新一次。

->这里先单独给出扩展JPanel类的Canvas 类

内部类

private class Canvas extends JPanel
	{
		private Random ran = new Random();
		
		public Canvas()
		{
			this.setBackground(Color.BLACK);		//设置中间容器的背景色为黑色
		}
		
		protected void paintComponent(Graphics g) //重写 绘制组件自身 方法
		{
			super.paintComponent(g);
			String str = "*";
			for (int i=0 ; i<500 ; i++)
			{
				int x = ran.nextInt(this.getWidth());
				int y = ran.nextInt(this.getHeight());
				g.setColor(new Color(ran.nextInt(256),ran.nextInt(256),ran.nextInt(256)));
				g.setFont(new Font("宋体" , Font.BOLD , ran.nextInt(40)+10));
				g.drawString(str, x, y);
				
			}
			
		}
	}

下面给出完整代码

package cn.com;

import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.Random;
import javax.swing.Timer;
import javax.swing.JFrame;
import javax.swing.JPanel;

public class StarrySky extends JFrame
{
	//定义内部类Canvas
	private class Canvas extends JPanel
	{
		private Random ran = new Random();
		
		public Canvas()
		{
			this.setBackground(Color.BLACK);		//设置中间容器的背景色为黑色
		}
		
		protected void paintComponent(Graphics g) //重写 绘制组件自身 方法
		{
			super.paintComponent(g);
			String str = "*";
			for (int i=0 ; i<500 ; i++)
			{
				int x = ran.nextInt(this.getWidth());
				int y = ran.nextInt(this.getHeight());
				g.setColor(new Color(ran.nextInt(256),ran.nextInt(256),ran.nextInt(256)));
				g.setFont(new Font("宋体" , Font.BOLD , ran.nextInt(40)+10));
				g.drawString(str, x, y);
				
			}
			
		}
	}
	
	public StarrySky()
	{
		init();
		
	}
	
	private void init()
	{
		//定时器
		Timer timer = new Timer(300 , new ActionListener(){
			public void actionPerformed(ActionEvent e)
			{
				repaint();			//直接刷新窗口
			}					
				});
		timer.start();
		this.setContentPane(new Canvas());			//添加面板到容器
		this.setSize(600, 480);
		this.setLocationRelativeTo(null);			//将窗口将置于屏幕的中央
		this.setVisible(true);
		this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		
	}
	

}

package cn.com;

public class Test 
{
	public static void main(String args[])
	{
		StarrySky sky= new StarrySky();
		sky.setTitle("闪烁的天空");
	}

}

有喜欢的小伙伴请点个赞吧~~~

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值