Demo, Video Settings, Culling

Published August 24, 2009
Advertisement


Aquarius Demo (with Ninja Demo)


Here's my water game prototype so far. There isn't anything to do except bother the snakes. Today, I did some profiling with the Shiny profiler, made the level update loop more efficient, and suddenly my app runs faster with vertical-sync on than without. What the hell? I don't know why yet, but I must be doing something very wrong with it disabled. So if you try the demo, run Aquarius with v-sync on. The ninja app has a slight delay in response time with v-sync enabled. They both use the same config file, so you have to change it when you switch, sorry. I didn't want to create a separate installer for the ninja test because its so small. Hopefully it installs and runs ok. Let me know if it doesn't?

I've been playing a lot with the particle system in Aquarius (still working title). The particles are now little tiny circles, and theres a few different sizes stored in display lists. I've added culling, the ability to change the video settings from the menu, and I changed the snakes' behavior a bit.

Oops, I forgot to included a list of the controls again.

Aim with the mouse
E, LMB - move forward
D - move backward
roll the mouse wheel - zoom in/out
R - grow a little bit and get faster ( but not much )
W - toggle wireframe (weirdness with the collision shapes atm)
C - toggle collision render
P - toggle particle update
Esc - back to menu, quit
F2 - toggle window mode
Pause - pauses just for you

Video Settings


The video settings can now be changed from the main menu. They're stored in the config file (which is now XML). I'll have to write a proper GUI_Page class to handle menu pages so I can put it on an Options page. When a setting is changed in the menu, a simple VideoSettings struct is updated, and the 'Apply Settings' button resets the video mode using SetVideoMode() (same as the fullscreen toggle). When I create that GUI_Page class, I'll have to make sure the app takes you back to the correct menu page.

There is a bug that I can't duplicate: One time, when going from fullscreen back to windowed mode, the viewport stayed at the upper-left of the monitor- within the window. So I dragged the window to the upper left and back, and it was back to normal. Bizarre.
Another annoyance is that going fullscreen moves Windows' folders around. I have no idea how to fix it.



Culling


I'm using a simple culling technique based on bounding circles. It takes the distance from an object to the screen center, and subtracts the bounding radius of the object from the bounding radius of the screen. I could test the object's radius against a rectangle for the screen, but it might actually be a little slower since the cost of this (extremely simple) technique is in the squareroot operation already needed to get the distance. There is a bit of wasted space around the screen (shown in the image). I haven't compared the operations for an AABB technique to this method at a low level, but I don't think there would be much to gain from using AABBs instead.

Each object's bounding radius is calculated by finding the furthest vertex, or circle + radius, from the origin. This is done once, when the object's Collision shape is created. The objects are culled by placing only visible entities into a vector of Entity pointers each update. I loop through every object and call it's UpdateCulling() method, which I pass the camera's position and current radius. This method returns true if the object is within the radius, and is added to the vector of objects to render.
0 likes 3 comments

Comments

coderx75
Looks cool!

I was reading about your culling technique and noticed that you're using a square root on distances. You should be able to factor this out. Squaring two sides of an equation yields a valid equation, so, distance < distance is the same as distance^2 < distance^2.

Instead of this:

distance1 = sqr ((x2 - x1)^2 + (y2 - y1)^2)
if distance1 < distance2 {
...
}

You could say:
distance1 = (x2 - x1)^2 + (y2 - y1)^2
if distance1 < distance2^2 {
...
}

Just thought I'd point out this little optimization if you haven't caught it already. Hope this helps!
August 29, 2009 09:06 AM
coderx75
Looks cool!

I was reading about your culling technique and noticed that you're using a square root on distances. You should be able to factor this out. Squaring two sides of an equation yields a valid equation, so, distance < distance is the same as distance^2 < distance^2.

Instead of this:

distance1 = sqr ((x2 - x1)^2 + (y2 - y1)^2)
if distance1 < distance2 then...

You could say:
distance1 = (x2 - x1)^2 + (y2 - y1)^2
if distance1 < distance2^2 then...

Just thought I'd point out this little optimization if you haven't caught it already. Hope this helps!
August 29, 2009 09:14 AM
zarfius
I think you'll find a bounding box may be a better option in this case. Consider the following function (off the top of my head):


bool InsideScreen(Screen screen, Object object)
{
   if(object.bottom < screen.top)
     return false;

   if(object.top > screen.bottom)
     return false;

   if(object.left > screen.right)
     return false;

   if(object.right < screen.left)
     return false;

   return true;
}


In the best case, your object is above the screen and will be culled in the first if statement. In the worst case your object is inside the screen and will take 4 if statements to not be culled.

This works well based on the assumption most of your objects are outside the screen most of the time (if they are not your probably not benefiting from culling anyway).

Now you just have to figure out if 1 to 4 if statements is faster than a single square root.
August 31, 2009 02:11 AM
You must log in to join the conversation.
Don't have a GameDev.net account? Sign up!
Profile
Author
Advertisement
Advertisement