Jump to content
  • Advertisement
Sign in to follow this  
Tarviathun

Object Management

This topic is 5029 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Maybe I am doing something totally wrong here or missing something so maybe you guys can help me out. I have not had any problems so far but at most I have had 30 "sprites" on screen at a time but for me the big bottle neck is the actual drawing (SDL 2d cus OpenGL is actually slower on my card). The object management is actually pretty lite, here is a brief outline:

large object list consisting of references to every potentially visible item currently in the game world (the map). Each object has a virtual update function that gets called every frame.

a map of tile objects. each tile contains a reference list (sorted by y then x axis) of objects on it as well as base information(base image and details drawn before sprites) and overlay (drawn over sprites) objects.

Every frame loop through the large object list and call the update function for each object.

If an object moves and it's new position is on another tile, it pops itself off of the current tiles container list and inserts onto the new tiles list. When an objects position changes, it also pops itself from a large render list of all objects sorted by y then x axis and reinserts itself via a binary search from it's last location in the render list based on direction of travel.

Figuring out which object to start drawing first depends on how much overdraw I have to allow for (largest sprite size). depending on yours you just grab the object list from the first tile you want to draw and use the first object as the head of your objects to render loop and end at the last object on your last tile (this is precomputed before i begin the loop). Then my rendering loop consists of drawing the base of the map, then the objects, then the overlays which for me are handled just like drawing the tile base.

Like I said, maybe I am doing something totally wrong here or maybe I am missing something, but I don't see this being a problem for me later on.

Share this post


Link to post
Share on other sites
Advertisement
Quote:
Original post by evillive2
Maybe I am doing something totally wrong here or missing something so maybe you guys can help me out. I have not had any problems so far but at most I have had 30 "sprites" on screen at a time but for me the big bottle neck is the actual drawing (SDL 2d cus OpenGL is actually slower on my card). The object management is actually pretty lite, here is a brief outline:



Yes, drawing is almost always the operation that takes the longest to perform. That's why I stated earlier that it wasn't *that* ultra-super-important to try and cut corners when you are updating your objects, because the real bottle-neck is in the drawing.

Share this post


Link to post
Share on other sites
Quote:
Original post by Tarviathun
BTW, what does rect-tested mean and what's your action area?


rect-tested, means that we do rect-in-rect tests for all tiles and other graphics before they are sent to the renderer, they are rejectect if they are entirely outside the screen, (the fastest way to draw is not to draw ;-D)

our action area, is a diamond shaped sub-segment of the map that is ncols and nrows big, this area is determined by doing calculations to decide what tile the view is looking at, and then selectiing a certain displacement negative and positive from that center tile, anything that is inside the action area (which is much larger than the view area) gets proccessing done to it, AI, etc

things outside the action area only get minimal proccessing, which ususaly come from outside events *such as a timer object elapsing, etc*

here is a diagram that might visusalize things better...

Share this post


Link to post
Share on other sites
Wow, that's an interesting idea about doing minimal processing outside the action area. But how exactly do you define "minimal processing"? The only thing I think I need to concern myself with in my game (at least for now) are sprite movements outside the view area. When an object is inside your action area, what additional processing do you to to those objects?

Share this post


Link to post
Share on other sites
what you do is really up to you,

you could have multiple concentric areas,

think of it as Proccessing LOD, the innermost visible layer proccesses most heavility (all AI features, audio, etc,etc) next level, only tracking for the player, third level, only events that are sent to it *that is, it wont be polling anything*

the thing that makes this method great, is you can define a region as a sub-segment of your map, by finding the center of your view, the normal 'costly' method is to check the distances of everything to where you are, which eliminates the value of area-based action (since you have to examine each sprite) with this, you can query outward as much as you want, as long as your map tiles know what is on them.


A good way to think about how this would work, is like...

Zombies =D

at least how they are classified in Night of the Living Dead, that is

if they are far away and with no 'stimulus' they kinda just lumber around (very little action) but when somthing gets close to them, they become more excided (heavy more precise proccessing) =D

Share this post


Link to post
Share on other sites
That's actually a really cool idea, EDI, and thanks for the explanation. I sorta feel stupid about it.

I pretty much believe that everyone's right and I'm wrong about what to worry over. I'll see if I can combine a lot of these ideas and concepts into a single functional RTSUnit manager.

I'll probably utilize a matrix/list idea, where I sort the matrix by location and the object list just sort of sits on its own. For the active area idea, I might not be able to do that, seeing as I'm making an RTS engine and I need to constantly keep all units up-to-date. However, I could easily create a function that generated a list(much like the way I render tiles) based on the camera location, where I could pass the manager's update function that list instead of the whole unit list.

The main reason why I'm so concerned about efficiency here, is pathfinding. It's really really costly and I'm worried that I'm going to do it in a very poor manner, and cause the whole system to lag. I'm also afraid that I don't have enough knowledge to find a more suitable method to find paths other than basic A*. Anyways, that's why I'm worried about it.

Share this post


Link to post
Share on other sites
this may not help you, but it is somthing to 'chew' on.


if i had to guess i would say at least 80% of the time, when moving a unit, you are moving it in a straight line.

with this asumption, you can first do a cheap *breshenhem(sp?)* line algorythm to test start point to end point for no obstructions, if there are no obstructions, simply walk that line that was formed, and dont bother doing A*

if there is however, then fall back on A*, using progressivly complex forms of pathfinding is a good idea i think, much in the way you first test for being inside a rectangle, before testing pixel-perfectness, when hit testing.

if you assume that most of the time your paths wont be complex (which i belive is true, depending) and then implement a 'train' of methods that start very simply, and can 'fail fast' if it is found that it cant make a path, and then fall back on the next, the last being full-map pathfinding, etc.

Follow me?

Share this post


Link to post
Share on other sites
Hi guys,

I was about to make a new topic about a similar problem, so I'll just add it here. I'm currently working on a tile-based game, and I have built a generic tile-based engine for it so I can use it in future projects as well. Now the problem I'm having is actually a software architectural problem, but I think it better fits in this forum. I'll give an overview of the engine.

I have a basic Landscape class, which loads map data from a file and prepares them in memory for fast an efficient rendering. It loads tile textures and object textures into memory and creates all the objects (walls, towers, trees, etc) on the map. Now to keep my engine game-independant, I use a base ObjectInstance class, that only holds rendering information (how to render the object, its x/y size, ...) but nothing else. Objects are managed by placing a pointer to the ObjectInstance located on a particular tile in the main tile array. Using a list would be possible too, but it won't solve my problem.

Of course, in my game, I don't just use ObjectInstance's for all my objects. I derive classes from ObjectInstance like Wall, Unit and Tower, and I add additional functionality to these classes. The problem I'm having now is that, because my engine doesn't know derived classes, it can only return a pointer to an ObjectInstance when I'm for example asking for the object located at (25,3). So if my player damages another unit, there's no way I can call the doDamage() function on Unit. Of course I can do a dynamic_cast, but that would be quite an awkward and ugly solution.

So there's my question: how do you guys manage a generic list of objects made out of different derived classes, without using ugly language structures (dynamic_cast)? Another solution would be to keep different lists for each object type, but that would be pretty unefficient as well. Using an abstract base class is impossible too, as functionality can differ greatly between games.

So how would you solve or have you solved this problem? Thanks a lot!

Share this post


Link to post
Share on other sites
Well, lets see if I have this right.

>>The problem I'm having now is that, because my engine doesn't know derived classes, it can only return a pointer to an ObjectInstance when I'm for example asking for the object located at (25,3). <<

from that line, i gather somthing like this is happening


ObjectInstance* oi=landscape.getObject(x,y);

but in reality, the object there is of type, oh, 'BossCharacter', so you would have to do,

BossCharacter* bc=(BossCharacter*)oi;

which works (note i know that doing it that way is 'unsafe')

so, if you would rather not do that cast, your only solution is to create a subclass of your Landscape class, that is more game-specific, and within that subclass write specialized methods, such as

getBossCharacter(x,y);

which does the cast for you,


I think your problem might be, that while you are allowing for subclassing to happen to your map objects, your not allowing for that same functionality for your map, and other objects, for instance...



game layer - [sprite]
engine layer-[map][object]

without subclassing map, you dont have a place to put, game specific map logic.


am I on the right track?

Share this post


Link to post
Share on other sites
Exactly, you're spot on. A cast would solve all my problems, but I've been taught hundreds of times that having to do a cast is a sign of bad design, and indicates that you should rework your engine. So it's indeed the (BossCharacter*) cast that I refuse to use. I already use a derived Landscape class, but I always end up with real ugly code.


The first approach I tried was the following:
When creating a boss character in the derived Landscape class I'd get the following sequence:
BossCharacter *b = new BossCharacter();
bosslist.push_back(b);
addObject(b);

With addObject(ObjectInstance*) a function from Landscape that adds the character to the engine and the map. If I'd need the specific boss functionality later, I'd pick the boss from the list. The problem with this is of course that it simply doesn't use the efficient object access provided by Landscape, and that I need to manage a whole bunch of lists for all object types. Very cumbersome.


The second approach I tried was that I'd put a virtual issueAction(Action) function in the basic ObjectInstance class, that I overrided for all the derived classes. Action was just a container with some data that indicates what the action might be. The problem with this is flexibility. If, for example, one character was going to give an item to another one, I'd have to somehow pass on a pointer to the other character AND the item in issueAction(). Every action required different data to be passed on, resulting in a lot of void pointers and casts and crap like that.


I couldn't get the second approach to work properly, but the first one did. It was just bloody ugly and became even uglier when the project grew, so that's why I made the post.

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!