Archived

This topic is now archived and is closed to further replies.

LessThanJoe

Efficency

Recommended Posts

LessThanJoe    122
all rightyo, I''ve a 2d array that is 800x600. Each spot holds a number 0-4 for the color I want at that spot. When outputing this...1 pixel at a time, would it be best to: // by output here, i mean do a glVertex3f just loop through set the color every single time output each point... or set the color loop through while searching for that color output points that have the matching color repeat for every color Thanks

Share this post


Link to post
Share on other sites
Guest Anonymous Poster   
Guest Anonymous Poster
Both of those methods are going to blow. Hard. It doesn''t sound like you want to be using OpenGL for whatever you''re doing.

-- John

Share this post


Link to post
Share on other sites
LessThanJoe    122
Thank you for that encourging advice...but for now I am making a simple 2d tank game, and am more concerned with making the code for the game then the code for the graphics. After I finish this, I will procede to learn how to work with more 3d programs and let OpenGl do the work for me.

Could someone please tell me which of those two methods will be quicker. Thank you.

Share this post


Link to post
Share on other sites
Michalson    1657
Actually he''s right. I assume you''re doing some sort of Worms/TankWar/Take turns shooting at angle game. I would suggest two things. 1) Switch to DirectX 7 and use DirectDraw (which can be made more efficient for lots of single pixel sets) or 2) Using OpenGL, create a bunch of big (256x256) textures that can cover the screen (tiled across the screen). Modify these textures rather than trying to mess with the screen.

In response to your orignal query, the first method would seem best (though you should test both with a profiler to be sure). The second method is likely to cause alot of cache misses and more importantly the overhead of doing 4 IFs for every pixel would be huge.

Share this post


Link to post
Share on other sites
LessThanJoe    122
I just kind of realized something. Like right now, I am doing a deformation that creates a hole in the terrain, and I wrote the code that changes the 2d array. Would it work if I added in the code that changed the pixel colors in with this then just do a SwapBuffers when I want to output something?
(paraphrase, basically OpenGl will store the terrain for me and I just change the pixels I want changed.)

Now that this concept is in my head, it looks like it would be fairly easy to code. I'm going to take a break from coding for a while, hopefully someone will tell me if this thing I'm doing is possible.

If this new method would work, do you think the first method I listed would be best to use when I first draw the terrain at the begining (The lag would be acceptable and considered as load time)

[edited by - lessthanjoe on May 4, 2002 7:23:07 PM]

Share this post


Link to post
Share on other sites
Beer Hunter    712
Maybe you could treat the terrain as a large polygon / set of polygons. It''d make drawing a lot faster, and reduce memory usage, but collision detection and terrain deformation would be harder. Overall, I think it would be faster...

Share this post


Link to post
Share on other sites
LessThanJoe    122
Rather then just repeating to use tiles, could someone please explain to me how I am supposed to use tiles. Should I make 20 40x30 2d arrays? Then what? How would outputting these to the screen be any different.

Has anyone here made a worms game? How did you impliment the terrain?

Thanks for tolerating the unlearned.

Share this post


Link to post
Share on other sites
Beer Hunter    712
There was a discussion on #gamedev a long time ago about this. We figured that worms 2 used polygons. There was no way that it could have stored all that data on a per-pixel basis, and still drawn it that fast.

Share this post


Link to post
Share on other sites
LessThanJoe    122
How would I do the terrain by using polygons?
Is this something like makeing 1 large polygon with the max height for every pixel (an array that the index is the x value and the value for each index is the height for that x point) being the vertices...then throw in the bottom right and bottom left to make it a complete polygon? Aside from making dirt fall when areas below it are taken out, this actully seems to me like it would be fairly easy to impliment...and even better, then random point generation code already works for this.

Also, I've never seen the games worms, only scorched earth and pocket tanks...so try to keep any examples to those two if you need to use examples.

(Edit: reworded something to make more sense)

[edited by - lessthanjoe on May 5, 2002 9:03:30 PM]

Share this post


Link to post
Share on other sites
Beer Hunter    712
The polygons would have arbitrary x and y co-ordinates.
I don''t know how to make terrain fall with polygons. Why would you want it to? It would only limit the amount of strategy in the game (one of the things which always bothered me about scorched earth).

Share this post


Link to post
Share on other sites
LessThanJoe    122
Say I''m storing the polygon in an array as stated above...now say someone shot a hole in the side of a cliff, creating several different verticies on the same x axis...what will I do?

Share this post


Link to post
Share on other sites
Beer Hunter    712
That situation doesn''t work out if you store the data like that... I don''t suggest it. I''m suggesting that a polygon''s vertices could be anywhere on the screen.

Share this post


Link to post
Share on other sites
LessThanJoe    122
so now I''m thinking of storing all of the data in a 2d array, having 1 col store the x values, and another store the y values. I''d have to write something that makes sure all of the x values are in order, but that shouldn''t be tough.

Honestly, if this method appears to have any problems, I''m not changing the layout of my program again, I''ll just hardcode my way past any problems *evil grin*.

Share this post


Link to post
Share on other sites
Guest Anonymous Poster   
Guest Anonymous Poster
I think you loched yourself to the thinking of that you need all the pixels on the screen in one array.

A tile is a prebuild block of data (an small image) that fits together with other blocks, so that you can make large levels with just a few small components (lego?) this is usually the way all old 2d games use gfx because it take less memory, faster to build levels and easy to give the tiles properties (like ''here you can walk'', ''here is a swamp an you will slowly sink'', ''here is a hole and you will fall down'' and so on.) then you can apply one tile to one quad (or two triangles if you like that better) and fill the screen with these quads.

Share this post


Link to post
Share on other sites
LessThanJoe    122
I understand how tiles work, but this is a scorched earth/worms clone, so I need to be able to deform the terrain. Terrain deformation the way I want it done cannot be done with tiles (well, obviously it can, but not while maintaining any ease).

Now, here is another problem I'm having. I have some code that is supposed to form a square ditch or piller, but rather then doing that, one side is flat and the other is slanted. Even stranger is, I don't think the flat and slanted sides are even...it's kind of to the right of the center. I'm not sure if this has to do with OpenGL or just my code that changes the array is bad. Either way, you all seem to know more about the game I'm making then me, so I guess this is a good a place as any to do.

Now, here is the code that does the changes to the array

      
void Piller(terrain &TheField, int x, int width, int dist)
{
for (int counter = 0; counter < dist; counter++)
{
if (dist > 0)
TheField.Deform(x, width, true);
else
TheField.Deform(x, width, false);

DrawTheTerrain(TheField);
}
}

void terrain::Deform(int &x, int &width, bool direction)
{ // true for down, false for up

int counter = 0;

// move the center point

if (direction)
MyTerrain[x]++;
else
MyTerrain[x]--;

// check to make sure it's in bounds

if (MyTerrain[x] < 0)
MyTerrain[x] = 0;
if (MyTerrain[x] > 600)
MyTerrain[x] = 600;

// move the rest of the points

for (counter = 0; counter < (width/2); counter++)
{
//if (x - counter >= 0)

MyTerrain[(x - counter)] = MyTerrain[x];
//if (x + counter < 800)

MyTerrain[(x + counter)] = MyTerrain[x];
}
}


And here is the code that does the drawing


        
void DrawTheTerrain(terrain &A)
{
int x = 0;

glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); // clear screen and depth buffer

glPushMatrix();
glLoadIdentity();

glBegin(GL_POLYGON);

// starting point, sets color to blue for gradient

glColor3f(0.0f, 0.0f, 1.0f);
glVertex3f(0.0f, 600.0f, -1.0f);

// set color to green, place all the top points

glColor3f(0.0f, 1.0f, 0.0f);
for (x = 0; x < A.MaxX(); x++)
glVertex3f(float(x), float(A.GetY(x)), -1.0f);


// bottom right, blue point to make gradient

glColor3f(0.0f, 0.0f, 1.0f);
glVertex3f(800.0f, 600.0f, -1.0f);

glEnd();
glPopMatrix();

SwapBuffers(g_HDC); // bring backbuffer to foreground

}



The variables should be fairly self explaintary.

Note: I made a program that couted the numbers in the array, and aside from the fact that the width was 1 less then it should be, there was no problem with the array mod code. Therefore OpenGL is to blame.

(2nd edit, added in the note and 2 source tags)


[edited by - lessthanjoe on May 7, 2002 10:47:55 AM]

Share this post


Link to post
Share on other sites
MatrixCubed    199
#1 - What about using a 1D array; each index represents a X-value along the terrain/level/screen, and each value in the array represents the height at that level.

#2 - When you render to the screen, draw vertical lines (GL_LINES), I guess you could texture them too if you absolutely wanted some funky effects on the screen.

#3 - When a shot is fired and explodes on the screen, you could alpha blend the result blast to remove the pixels that should be affected (to show where the blast radius took effect), then decrease the Y-value of the array-terrain (from #1) by however you would calculate the vertical displacement (I think we did this in grade 10/11 trigonometry, but I''m sure there''s a simplistic way to do so).

#4 - You might consider rendering in different layers (a la Super Nintendo side-scrollers), for example:


  
|1---------------Background (for scrolling)---------------|
|2------------------Tanks/PlayerObjects-------------------|
|3-------------------Deformable Ground--------------------|
|4------------------Projectiles/Explosions----------------|
|5-----------Foreground (for misc effects, HUD)-----------|


This essentially means you''re rendering object back-to-front based on object type (background, tank, shots, etc).

When you have to render 3, you compose it to an offscreen texture; when shots deform the ground, you can alpha blend layer 3 using textures, and remove the pixels'' alpha component with a BlendFunc (I forget what an appropriate one might be). Then render back-to-front as normal.

I hope this helps... good luck!

- M

Share this post


Link to post
Share on other sites
LessThanJoe    122
Yeah, I already had it planned like that. My problem right now is I''m working on getting the terrain to do everything I''m going to need it to do, and I can''t even get the firt deformation to work right. Anyway see the problem in that bit of code?

Share this post


Link to post
Share on other sites
a person    118
only a moron or a sadistic coder who knew EXACTLY what they were would use opengl for this sort of game. switch to directdraw, it will save you a lot of headaches. DONT store ANYTHING that you will be reading from with opengl. you want terrain data in system ram not vram. you will kill the fraemrate worse then bashing the card with a block of ice. learn how to program first. this includes the very basics whihc you seem to have, then more advanced topics such as dynamic memory allocation, array usage, top down coding theory, logic problem solving, etc. you need to learn to break the problem down better. drawing the entire array to screen will be slow no matter what route you go. infintaly more if you read things from vram. look into things like dirty rects and using double buffering without the flip. this will allow you to update what changes and not worry about inconsistenceis a flip brings. again siwtch to directdraw, it will work much better. esepciallys ince the games you are trying to mimic used either directdraw or direct video access within dos. neither of which is opengl.

Share this post


Link to post
Share on other sites
zedzeek    528
>>I understand how tiles work, but this is a scorched earth/worms clone, so I need to be able to deform the terrain<<

i dont know exactlly what u want but to do scorched earth, just keep an 1d array of the terrain heights + draw lines for each xposition from the bottom of the screen upto the height of the terrain. very very quick on a slow opengl card u should manage this at about 100fps at 640x480 (200fps with a bit of optimization) with a gf2mx (like mine) u should aim for 500fps



http://uk.geocities.com/sloppyturds/gotterdammerung.html

Share this post


Link to post
Share on other sites
LessThanJoe    122
Only a moron who calls someone a moron and then tells them they are a bad programmer expects to get any results. I am writing this game as an aid to help me learn OpenGL.

quote:
DONT store ANYTHING that you will be reading from with opengl. you want terrain data in system ram not vram.

Please point me to the line(s) of code where I do this...as I clearly do not see them.

Does anyone here think that zedzeek's method would be better then using an array that stores the heights to make a polygon?

[edited by - lessthanjoe on May 11, 2002 12:16:53 PM]

Share this post


Link to post
Share on other sites
llyod    122

Yes, I believe zedzeek is onto the solution. If I remember Worms correctly, it indeed uses the method he describes, even if not in OpenGL. Why don''t you try it, shouldn''t be too much code to get it up and running!

Share this post


Link to post
Share on other sites