请问swing中的双缓冲怎么用啊?能给个简单的例子吗?
解决方案 »
- 初中物理公式中的导体电阻Java类构造
- drag and drop
- 大家看看怎么做啊?谢谢
- 日期格式问题
- 问一个问题
- 初学者的疑问about core java 1例4-1:CalendarTest.java
- 如何在Jbuilder7中在某个Panel中添加右键菜单
- 用java如何调用WORD
- 请问applet如何和页面上的其他本分交互,比如输出HTML文件,和象页面javascript一样操作页面元素
- 寻找包包...(请各位关注,谢~)
- rmi的java.rmi.server.codebase问题(分不多,还请各路好汉都来瞧瞧)
- 有没有办法根据表生成动态的insert delete update 方法呢?
JComponet默认实现了双缓冲的,其他组件继承这个类
如果没有必要,不用自己实现双缓冲
...
public void update(Graphics g) {
Dimension size = getSize();
if (doubleBuffer == null ||
doubleBuffer.getWidth(this) != size.width ||
doubleBuffer.getHeight(this) != size.height)
{
doubleBuffer = createImage(size.width, size.height);
}
if (doubleBuffer != null) {
//向双缓冲中绘图
Graphics g2 = doubleBuffer.getGraphics();
paint(g2);
g2.dispose(); //显示双缓冲中的内容
g.drawImage(doubleBuffer, 0, 0, null);
}
else {
paint(g);
}
}public void paint(Graphics g) {
// do drawing here
...
}
AWT中的双缓冲我会。
请帮帮忙,给我说下swing中所谓的自带双缓冲怎么用?
有没有提供什么可以操作后台图象的方法呢?
大家帮帮忙啊,我找了好久了。
public void setDoubleBuffered(boolean o)
Swing's double buffer mechanism uses a single offscreen buffer per containment hierarchy (usually per top-level window) where double-buffering has been enabled. And although this property can be set on a per-component basis, the result of setting it on a particular container will have the effect of causing all lightweight components underneath that container to be rendered into the offscreen buffer, regardless of their individual "doubleBuffered" property values. By default, this property is set to true for all Swing components. But the setting that really matters is on JRootPane, because that setting effectively turns on double-buffering for everything underneath the top-level Swing component. For the most part, Swing programs don't need to do anything special to deal with double-buffering, except to decide whether it should be on or off (and for smooth GUI rendering, you'll want it on!). Swing ensures that the appropriate type of Graphics object (offscreen image Graphics for double-buffering, regular Graphics otherwise) is passed to the component's paint callback, so all the component needs to do is draw with it. This mechanism is explained in greater detail later in this article, in the section on Paint Processing.
所以我想调用swing的off screen
如果我不想把已经做好的程序保存在一个图象中,我该如何做?
如果是前者,你可以用背景的off screen,对于包含Swing子组件的,你最好别这样做(其实差不多是没法做)我猜你是在做什么画图的东西才这么问的吧???
就是想做个小的画图板
现在不知道在swing中怎么将画出的东西保存下来
请大哥介绍个方法给我。
不胜感激
doubleBuffer = createImage(size.width, size.height);当你的程序的内部数据变化的时候,比如用户新画了一条线,在事件响应函数里你向Image绘图:
Graphics g2 = doubleBuffer.getGraphics();
//更改绘图......;
g2.dispose();然后你通知Swing准备重绘:
repaint();在paint方法里,你就不用再去绘图了,直接把画好的image拿出来
g.drawImage(doubleBuffer, 0, 0, null);如果你的绘图可以把计算限定在某一个区域,那么用update方法更好,因为update并不擦除背景(如果它本身是轻量级组件),你可以增量重绘,这是最好的方法,但是不幸的是,大多数情况很难对某一个特定的区域重新计算,所以JComponent的update方法默认实现直接就调用paint()。
可是在swing里不是默认实现了双缓冲了吗?
上面的方法我试过,但是
doubleBuffer = createImage(size.width, size.height);
g.drawImage(doubleBuffer, 0, 0, null);
第二句总是提醒我找不到源image。而且抛出空指针异常。
是不是createImage的调用者不对啊?我这里是一个JInternerFrame
import java.awt.Graphics;
import java.awt.Image;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;import javax.swing.JFrame;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
public class MyPanel extends JPanel {
Image doubleBuffer;
int clickCount;
private static final Dimension pSize = new Dimension(300, 300);
public void paint(Graphics g) {
long t1 = System.currentTimeMillis();
if (doubleBuffer == null) {
doubleBuffer = createImage(this.getWidth(), this.getHeight());
}
g.drawImage(doubleBuffer, 0, 0, null);
long t2 = System.currentTimeMillis();
System.out.println("Render consumed " + (t2 - t1) + " milliseconds");
}
public Dimension getPreferredSize()
{
return pSize;
}
public void changeInternalStatus()
{
Graphics g2 = doubleBuffer.getGraphics();
//更改绘图......;
g2.drawLine(0, clickCount, doubleBuffer.getWidth(null), clickCount);
clickCount += 5;
g2.dispose();
repaint();
} public static void main(String[] args) {
final MyPanel p = new MyPanel();
JFrame f = new JFrame();
JMenuBar mb = new JMenuBar();
JMenu m = new JMenu("Test");
mb.add(m);
JMenuItem mi = new JMenuItem("Draw in off screen");
m.add(mi);
mi.addActionListener(new ActionListener(){
public void actionPerformed(java.awt.event.ActionEvent e) {
p.changeInternalStatus();
}
});
f.setJMenuBar(mb);
f.setContentPane(p);
f.pack();
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.show();
}
}建议你看看http://java.sun.com/products/jfc/tsc/articles/painting/index.html
Render consumed 0 milliseconds
Render consumed 0 milliseconds
Render consumed 0 milliseconds
Render consumed 0 milliseconds
Render consumed 0 millisecondsimport java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;import javax.swing.JFrame;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
public class MyPanel extends JPanel {
Image doubleBuffer;
int clickCount;
private static final Dimension pSize = new Dimension(512, 512);
public void paint(Graphics g) {
long t1 = System.currentTimeMillis();
if (doubleBuffer == null) {
doubleBuffer = createImage(this.getWidth(), this.getHeight());
}
g.drawImage(doubleBuffer, 0, 0, null);
long t2 = System.currentTimeMillis();
System.out.println("Render consumed " + (t2 - t1) + " milliseconds");
}
public Dimension getPreferredSize()
{
return pSize;
}
public void changeInternalStatus()
{
Graphics g = doubleBuffer.getGraphics();
//更改绘图......;
g.drawLine(0, clickCount, doubleBuffer.getWidth(null), clickCount);
clickCount += 5;
for (int i = 0; i < 256; i ++) {
g.setColor(new Color(i, i / 2, i / 3));
g.drawRoundRect(i, i, this.getWidth() - i * 2, this.getHeight() - i * 2, i / 5, i / 10);
}
g.dispose();
repaint();
} public static void main(String[] args) {
final MyPanel p = new MyPanel();
JFrame f = new JFrame();
JMenuBar mb = new JMenuBar();
JMenu m = new JMenu("Test");
mb.add(m);
JMenuItem mi = new JMenuItem("Draw in off screen");
m.add(mi);
mi.addActionListener(new ActionListener(){
public void actionPerformed(java.awt.event.ActionEvent e) {
p.changeInternalStatus();
}
});
f.setJMenuBar(mb);
f.setContentPane(p);
f.pack();
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.show();
}
}这个是不用double buffer的,控制台输出为
Render consumed 16 milliseconds
Render consumed 47 milliseconds
Render consumed 15 milliseconds
Render consumed 31 milliseconds
Render consumed 16 milliseconds
Render consumed 47 milliseconds
Render consumed 16 milliseconds程序:
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;import javax.swing.JFrame;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
public class MyPanel extends JPanel {
int clickCount;
private static final Dimension pSize = new Dimension(512, 512);
public void paint(Graphics g) {
long t1 = System.currentTimeMillis(); //更改绘图......;
g.drawLine(0, clickCount, this.getWidth(), clickCount);
for (int i = 0; i < 256; i ++) {
g.setColor(new Color(i, i / 2, i / 3));
g.drawRoundRect(i, i, this.getWidth() - i * 2, this.getHeight() - i * 2, i / 5, i / 10);
} long t2 = System.currentTimeMillis();
System.out.println("Render consumed " + (t2 - t1) + " milliseconds");
}
public Dimension getPreferredSize()
{
return pSize;
}
public void changeInternalStatus()
{
clickCount += 5;
repaint();
} public static void main(String[] args) {
final MyPanel p = new MyPanel();
JFrame f = new JFrame();
JMenuBar mb = new JMenuBar();
JMenu m = new JMenu("Test");
mb.add(m);
JMenuItem mi = new JMenuItem("Draw in off screen");
m.add(mi);
mi.addActionListener(new ActionListener(){
public void actionPerformed(java.awt.event.ActionEvent e) {
p.changeInternalStatus();
}
});
f.setJMenuBar(mb);
f.setContentPane(p);
f.pack();
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.show();
}
}
但是这是有代价的,这个自己实现版本的不能够再添加新的子组件
这就是我为什么一开始不想让你自己实现off screen的原因
(因为你问我问的是swing的双缓冲怎么用,问法)
你看看http://java.sun.com/products/jfc/tsc/articles/painting/index.html
我觉得会对你很有帮助