ra4king
|
 |
«
Posted
2011-03-12 02:13:49 » |
|
What is the difference between double buffering by: -creating BufferedImage, drawing in it, and drawImage() onto screen, -using BufferStrategy.
I have only used BufferStrategy once and it doesn't seem that much different.
|
|
|
|
teletubo
|
 |
«
Reply #1 - Posted
2011-03-12 03:19:36 » |
|
BufferStrategy is way faster . I cannot quantize this "way faster" right now, but I remember a few years ago when I was developing my first java game I almost cried with hapiness when I changed double buffering with BufferedImage to BufferStrategy and gaind something like 20 FPS .
|
|
|
|
ra4king
|
 |
«
Reply #2 - Posted
2011-03-12 03:26:43 » |
|
Hmm, ok I will look into it a bit more. But I still don't understand how it is faster 
|
|
|
|
Games published by our own members! Check 'em out!
|
|
IronclawsBt
|
 |
«
Reply #3 - Posted
2011-03-12 04:19:53 » |
|
BufferStrategy has the option of pointer flipping. Instead of copying the off screen buffer to the screen's memory, the buffer simple says "Use this for memory the screen now". It is not only faster, but also reduces tearing.
|
|
|
|
ra4king
|
 |
«
Reply #4 - Posted
2011-03-12 04:50:01 » |
|
Oh so that's the difference!
Thanks!!
|
|
|
|
dah01
|
 |
«
Reply #5 - Posted
2011-03-12 06:40:11 » |
|
This is valuable knowledge. Do you have any code samples or links with exanples of the difference in implementing this switch? Is it a class-for-class swap or is there a drastic pattern change required?
|
|
|
|
|
|
|
ra4king
|
 |
«
Reply #7 - Posted
2011-03-12 20:45:50 » |
|
There is createBufferStrategy(int) in java.awt.Canvas and java.awt.Window. You call that first then get the BufferStrategy by calling getBufferStrategy(). All there is left is to getDrawGraphics() to get the Graphics object and then show() to show the image on the screen. Hope that helped 
|
|
|
|
dah01
|
 |
«
Reply #8 - Posted
2011-03-13 04:53:12 » |
|
It did! I think you are the flash, replying to all my threads.
|
|
|
|
|
ra4king
|
 |
«
Reply #9 - Posted
2011-03-13 04:57:09 » |
|
Oh wow I didn't know you were the OP of that other thread about AWT  Glad to help anyway 
|
|
|
|
Games published by our own members! Check 'em out!
|
|
philfrei
|
 |
«
Reply #10 - Posted
2011-03-13 08:29:27 » |
|
How does BufferStrategy differ from just using a Swing JPanel and drawing on that? JPanel automatically double buffers, doesn't it? Really simple to use. I can do redraws under 20msec with it.  It seems quite good for beginning simple animations, as well as move-based or puzzle-based games. The "smoke" the click&drag animation in Hexara http://www.hexara.com are all done that way.
|
"Greetings my friends! We are all interested in the future, for that is where you and I are going to spend the rest of our lives!" -- The Amazing Criswell
|
|
|
Alan_W
|
 |
«
Reply #11 - Posted
2011-03-13 11:42:33 » |
|
Generally go for bufferstrategy as buffer flipping is faster than bit copying. That is unless you are creating the entire screen image by manually manipulating bits in CPU memory, rather than on the GPU. In this case, you end up copying the entire buffer every frame anyway. If you implement BufferStrategy in this case, and the hardware doesn't support it, then you can end up copying the buffer twice every frame!
|
Time flies like a bird. Fruit flies like a banana.
|
|
|
ra4king
|
 |
«
Reply #12 - Posted
2011-03-13 19:51:03 » |
|
If you want to use JFrame or JApplet, then draw on a JComponent and then you don't need to worry about double buffering. If you want to use Frame or Applet, then draw on a Canvas and use BufferStrategy.
|
|
|
|
dah01
|
 |
«
Reply #13 - Posted
2011-03-13 23:58:18 » |
|
So, let me get this straight: You can simply draw on the panel and it will auto double buffer? That sounds perfect.
|
|
|
|
|
ra4king
|
 |
«
Reply #14 - Posted
2011-03-14 00:10:40 » |
|
I don't recommend drawing on a JPanel, try JComponent.
|
|
|
|
philfrei
|
 |
«
Reply #15 - Posted
2011-03-14 08:30:01 » |
|
Yes, you can draw on a JPanel and it automatically double buffers. ra4king is adamant that JComponent is better. There are probably good reasons and I defer to him, as I'm kind of cruising on the surface level of Java in many respects and have never used JComponent. But if you are looking for simplicity, you CAN do this: Top level, JFrame. Then, instead of trying to do anything fancy with the "content pane" of the JFrame, just add a subclassed JPanel and draw/animate your objects on that. Easy peasy. We are talking beginning, get feet wet, intro to Java game programming, nothing fancy. But one can do a fair bit with this set up. I think the main hazard/complication is that repaint() calls have to be done from some vantage point other than the JPanel itself, due to an aspect of "passive rendering". If you put your game loop or timer on the JPanel with the animation, the Event Dispatch Thread will think it can be "more efficient" by collapsing the repaint calls together rather than treating each one as a separate event. So, my solution has been to create a separate class with a Timer and have the Timer call the JPanel's repaint() function. I use the java.util timer, and set it to repeat calls every 30 msec or thereabouts. But you could do something similar with a game loop. Main point, the game loop or timer should not be part of the JPanel class you are animating. Do I hear howls of disagreement?  One can refactor in active rendering or other fancier animation schemes later.
|
"Greetings my friends! We are all interested in the future, for that is where you and I are going to spend the rest of our lives!" -- The Amazing Criswell
|
|
|
ra4king
|
 |
«
Reply #16 - Posted
2011-03-14 12:33:05 » |
|
JPanel is used as a container. You don't draw on a container, you draw on a component  And yes, I agree that calling repaint() is passive rendering, which is why it's good for beginners, but not recommended to keep doing. When I made a quick test, I went up to 100 FPS without the repaint() calls being collapsed together so it's not really that bad.
|
|
|
|
Riven
|
 |
«
Reply #17 - Posted
2011-03-14 15:21:46 » |
|
JPanel is used as a container. You don't draw on a container, you draw on a component  1
| public class JComponent extends Container |
 The reason to use JPanel over JComponent is that JPanel calls setDoubleBuffered(true) in its constructor, while JComponent does *not*.
|
|
|
|
ra4king
|
 |
«
Reply #18 - Posted
2011-03-14 18:36:14 » |
|
1
| public class JComponent extends Container |
 The reason to use JPanel over JComponent is that JPanel calls setDoubleBuffered(true) in its constructor, while JComponent does *not*. Yes yes I know  but try adding components to a JComponent  JComponent is automatically double buffered without any extra variables/method calls 
|
|
|
|
BoBear2681
|
 |
«
Reply #19 - Posted
2011-03-14 19:11:44 » |
|
The real gotcha is that JRootPane calls setDoubleBuffered(true) in its constructor, which causes all of its child components (i.e., everything) to be double-buffered, no matter what their value of their double-buffer flags are.
|
|
|
|
|
onlytoine
Senior Newbie 
|
 |
«
Reply #20 - Posted
2011-03-16 17:05:38 » |
|
Hello, It is my first message in this forum  The fastest way to render properly an image is to: - use a Panel (AWT) - use a BufferStrategy (Page Flipping) - use compatible images Other things to take care?  Toine
|
|
|
|
|
ra4king
|
 |
«
Reply #21 - Posted
2011-03-16 19:15:55 » |
|
Use Canvas instead of Panel, other than that you're good 
|
|
|
|
onlytoine
Senior Newbie 
|
 |
«
Reply #22 - Posted
2011-03-16 20:54:17 » |
|
Hey  Could you just tell me why canvas is better than panel? Cheers, Toine
|
|
|
|
|
ra4king
|
 |
«
Reply #23 - Posted
2011-03-16 21:04:36 » |
|
Because Canvas has access to BufferStrategy and, as the name suggests, it was made for drawing. Panel is only used as a container.
|
|
|
|
|