very bad fps when drawing large images

hi,

does anyone know if it’s basically possible to draw large background images (ie. 800x600) in Java2D games at a framerate of 50 fps?

i tried drawing a background image in different formats (gif, jpeg, png) but my framerate decreased dramatically. before i had stable 50 fps, afterwards only 35 or even worse.

the image format doesn’t really matter, once it’s loaded into memory, it’s basically converted to raw pixel data. The formats have to do with loading and compression, not rendering.

Are you rendering with BufferStrategy? Are accelerating the background image?

Your question has inspired me to write up a quick code that renders a background image at 800x600 (yes, I even drew an image for you :P). The FPS system is very dirty, it is not based on any timers or sleeping, it simply paints as many times as possible per second (which takes up most if not all of the computer usage, but it’s fullscreen anyway so that doesnt much matter).

Anyway have a look at the jar and tell me what FPS you get: Background.jar (~74kb), and you can find the source here

If you’re using Java 1.5, feel free to use nanoTime() instead. Anyway I got ~850 FPS running at 800x600x16 @ 75Hz.

thx for the test app. :o

nice image btw … :slight_smile:

on my machine it runs at around 950 fps/800x600x16@85Hz

yes, i’m using accelerates graphics/BufferStrategy according to kevin glass’ Java2D tutorial on www.cokeandcode.com
but it seems like i did something wrong.

could it be the fullscreen mode? my game is running in a 800x600 window (Canvas).

are you able to reach equally high framerates in window-mode, too?

I ran into the same problem. Drawing a background image (800x600 in size) every frame, brought down my FPS rate to about 10FPS and caused 100% CPU consumption.

I switched to drawing just the previous-background of Sprites that moved and things are much better, i.e. over 80FPS and minmal CPU consumption.

[quote]are you able to reach equally high framerates in window-mode, too?
[/quote]
hehe… not quite equally :wink:
At best you’ll get about 1/2 of the framerate you get in fullscreen. This is because fullscreen pauses the windowing system, but in windowed mode, you have to share the resources of the system.

I wrote another example for you. This example is not as agressive when it comes to painting, instead it pauses at the end of every loop to let the windowing system to do its minor business. This will keep things running smoothly (i.e. you can drag the window without it staggering or leaving blank spaces all over the screen). I did try to use agressive rendering but I only got an extra 15fps at the most.

You can find the example here: BGWindow.jar, and the source here: BGWindow.java

Feel free to resize the window to see the FPS difference you get in different sizes. The program starts out with the display (not the JFrame) at 800x600. The actual dimensions of the JFrame depend on border settings and other stuff. Give it a try! I got around 435FPS with 800x600x32 @75Hz

By the way, something interesting you should note. The background is 800x600 in size by default. When the display is this exact size, Graphics does not need to resize the image to fit the display. So technically, a smaller resolution than 800x600 can actually be SLOWER! (try 700x500 for example). But of course, teeny tiny sizes like 300x200 or whatever will be faster.

I run in 1600x1200 at 75Hz and I get 600 fps. :wink:

In a game though, you’ll generally want to cap it to 60 fps.

woogley,

thanks again for the demo. this will most likely boost my game’s graphics performance. :smiley:

although this does not belong to this thread, i’m curious, what does this code do:
keys[e.getKeyCode()&0xff] = 1;

don’t you get the same binary value again if you make a boolean AND with 0xff?
0x01 & 0xff = 0x01, right?

val&0xff means that the result cannot exceed 256. It’s done like that, because extended keys have a pretty high keycode, which would be outside of the array bounds.

00000101010101
&
00000001000111

00000001000101

0x01 & 0xff = 0x01, right?

Yes. 0xabcd & 0xff = 0xcd… and… 0xabcd & 0xff00 = 0xab00

ah, yes. sorry for the stupid question … :-[

my game runs now with an 800x600 background image at 50fps. woogley rulez! 8)

but there’s one thing:
since i changed my code to something similar to woogley’s code my game ignores all keyboard inputs as soon as i click into the game window.
if i don’t click everything runs fine. have a look here:
http://www.cocktailz.org/nb.html

any ideas about that? this problem is the last thing i have to fix before i can release the game.

Thanks :wink:

I would have to see some basic framework of your code but I’m guessing you’re rendering with a Canvas’ BufferStrategy and the JFrame is the one who’s actually handling the key events. When the Canvas gets focus (i.e. when you click on it), the JFrame no longer receives KeyEvents. What you can do is have JFrame implement KeyListener (if it isnt already) and use Canvas.addKeyListener(JFrame) so that both the JFrame and the Canvas can handle events.

That’s a random guess, for all I know you could be using a JPanel or something.

You could also use setFocusable(false) on the canvas, which would prevent the Canvas from getting the focus at all :wink:

aaah man, the solutions are so obvious and i didn’t see them. both of them work perfectly! :smiley:

thx a lot!

one more thing i’d like to ask:
when i run woogley’s BGWindow demo on my office laptop (win xp, ati mobility radeon 7500, intel pentium M 1.4ghz) i only get about 40 frames per second. is this normal for this hardware setup?

[quote]one more thing i’d like to ask:
when i run woogley’s BGWindow demo on my office laptop (win xp, ati mobility radeon 7500, intel pentium M 1.4ghz) i only get about 40 frames per second. is this normal for this hardware setup?
[/quote]
What JVM version?
It could be due to the JVM disabling hardware acceleration because it has detected an ati card.

the laptop’s jvm is 1.4.2_04