Advertisement

Vectors bouncing

Started by May 05, 2002 02:38 PM
20 comments, last by evilclown 22 years, 9 months ago
another good one is

for(;
{
int temp;
}

versus

int temp;
for(;
{ ...}

if you dont reference temp outside the for loop they will both generate the same code. in fact putting it in the for loop is safer. that keeps the scope very clear.

dont optimize for the compilier. code in a clear manner. the compilier doesnt always do it by the book. if it did it would suck.

consider both the above. the new variable in the loop looks nasty and would be if the compilier were forced to take it off the stack at the end of the loop . consider the variable outside the for loop ewww now its got a huge scope. the compilier is smarter then both of those cases.

worry bout algo''s not code tricks. generally speaking compiliers kick your butt anyhow in the code tricks department. just code what your trying to say. literally. say it in code. that should be your focus.

sigh but i have seen people gig''d by TAs on the first. its silly. in my view the first is better cause it limits scope and announces in code to a reader that i have no use for this variable beyond this loop. but scoping everything with { int temp; for(;{...}} is a tad silly too.


Is the smiley supposed to be a ; ) ?

Do I need to worry about optimizing at all? All I know is multiplying is faster than dividing, thats why i asked the x question.

Now how do I get the ball to move? Is there a better way than to find the rotation of the vector, and the magnitude. Then use cos and sin to find the new coordinates using that?

If so, Is there a faster way at finding the rotation besides doing
rotation = degtorad((1 / (cos (vector.x / vector.magnitude)))); 


I''m not sure if the degtorad is in the right place, but otherwise the above is supposed to mean:

rotation = cosinverse (x / r) 
Advertisement
in order:

1. worry bout your algo
1.5 worry bout calls to malloc/new and disc access
2. worry bout copying classes/structs
3. worry bout only having memory allocated as much as it is mutable.
4. worry bout efficient mathematics in a general form. (fast equations)


number 1) is well known worry bout looping.
number 1.5 (added in edit)) new and malloc ARE SLOW! call them only in key specific places. almost all games dont actually free/alloc memory while running. they just keep it all in a big pile a free/alloc privately. disc access is worse =/
number 2) i use
class foo
{
public:
//stuff
....
private:
foo(foo &f){;};
};

i use that ALOT. basically copying anything non trivial is expensive. unfortunatly every class in C++ has a built in memory copying foo(foo& f); constructor. its always there but there is no reason to use it normally. yet you do it gets called in places that you dont think of. so make the copy constructor private and copy via functions specifically.

number 3)
worry bout having 400 instances of a class that all have one field that is always the same value. as a rule you should try for only having as much mem allocated as is independantly changable.

and number 4)
a rip from quake3s mod code:
/*
===============
RotatePointAroundVector

This is not implemented very well...
===============
*/

those little blurps were all over quake2's mod code. "this could be better" etc. lots less in q3's i notice. basically code to finish while worrying bout the above. then after its easy enough to go back and rewrite the math to be fast. and it is a concern its just your last concern.

thats my list. not on it is worrying bout whether i++ is faster then ++i



[edited by - declspec on May 6, 2002 3:08:16 PM]
optimize algorithms.. for example this one:
for every vertex {
for every triangle {
if vertex is part of this triangle {
generate face normal
add face normal to vertex
}
}
}

that means you go through every triangle for every vertex.. an O(n*m) operation

if you do it like this:

for every triangle {
generate face normal
for each of the 3 vertices {
add face normal to vertex
}
}

(as you stored the indecees to the vertex array you find the vertices for free, just use the indecees)

result:

O(3*n) for the vector additions, O(n) for the crossproduct..

result is that for meshes with big polygoncount say 1024 vertices and 1024 faces (if this is possible..)
your amount of calcs go from 1024*1024 to 1024*4 (more or less)

a boost of 256!

algorithmic optimations are always great.. if your algo is short and clean structured, it normally is fast (means if you know what you do you are not too stupid to do it slow)

an other thing is data management object oriented programming can help there a lot but not at all if used wrong (you possibly know the scare cries uh virtual function calls are SLOW! they arent.. if used correctly.. means not perpixel please, but per object its no problem at all)

means structure your whole code to be fast.. this is easy for simple engines like this:

while(1) {
for every object {
object->Update();
object->Draw();
}
}

but gets difficult with networking and other stuff and fixed time steps but variable frame rate etc..

depends on what you wanna do

dont try to optimize onliners of code..

but make sure you don''t do some major faults:

if you know math, you can get rid of a lot of trigonometic funcion calls with trigonometric identities or a simple piece of paper..

example:
cosine(2x) == 2cosine(x)^2-1
if you calculate with halfangles (often used for fast perpixellighting) you can''t use for example this:
cosine(2x) = cosine(2*arccosine(x)) in a pixelshader.. those functions are simply not there in..

math functions used in your engine should not use that much if/else statements, for example in a vector class there should be no if/else (except for the normalization making sure /0 does not happen.. well except u use an automatic function taking care of this, namely some fast_reverse_square_root )

try to optimize the mathfuncs if you _WANT_ (like invert_matrix4x4 or something) but don''t try to optimize one-liners like that x = -x or something..

this is job of your compiler, not of you..

and if you write it in a normal way the compiler will have a big chance to recocnise this structure and says ahh! he wants to negate it! so well.. lets use an automated assember instruction wich simply changes 1 bit, the sign bit.. if this is fast on the cpu.. (the instruction is called fneg i think, but not 100% sure)

care about a fast collisiondetection algo, not about a fast sign-inversion-algo

for your main question:

if you have a surface normal vector, then a reflection for arbitary directions is this:

reflected = incomming - 2*dotproduct(normal,incomming)*normal

for a bottom floor the normal is for example (0,1) (1 is one in y direction, one up)

resulting equation:

reflected = incomming - 2*(0*incomming.x+1*incomming.y)*(0,1)

reflected = incomming - 2*incomming.y*(0,1)

reflected = incomming - (0,2*incomming.y)

this means your x-direction is not affected, but the y-direction gets

reflected = incomming.y - 2*incomming.y = -incomming.y

what the suggestions had for reflecting on the floor


got some ideas?

"take a look around" - limp bizkit
www.google.com
If that's not the help you're after then you're going to have to explain the problem better than what you have. - joanusdmentia

My Page davepermen.net | My Music on Bandcamp and on Soundcloud

Thanks for all the help.

I understood everything before "for your main question", whats a "surface normal vector".

Are you multiplying by (0, 1) because then on the ball vector, the y would change, but x would not?
A surface normal avector is a vector pointing "upwards" from the plane/polygon. eg if your polygon is lying flat on the origin the surface normal can be (0, 1, 0) or (0, -1, 0) depending on if the front of the polygon is facing up or down.Sorry dont know the answer to your other question
Advertisement
in 3d your bounce vector is...

bounceVector = surfaceNormal * -2.0f * DotVector( surfaceNorm, velocityVectorNormalized);

bounceVector now contains the true reflection in 3d...its normalized of course..so youll need to multiply your speed back into the vector.

oops thats supposed to be a += and not an =

so...

bounceVector += surfaceNormal * -2.0f * DotVector( surfaceNorm, velocityVectorNormalized);

ok now this is your 3d reflection vector
omg... omg. that is sooo right and soooo easy. *sighs at self* you dont understand we worked this to death in 2d. and i read your final version. and im like naw thats always going to be up. then i saw the += *flash of light* think to self: omg that is soooo right and sooo easy. sorry endo.


yeah, it is a very easy and very fast equation..

dotvectors are pretty powerful operations when you know how to use them. some hardwares now have dotvector operations built right onto the chip, so its just a couple of asm instructions..though youll probably have to overload your dotvector routine with straight assmebly to get full optimization..

something like...

extern inline f32 DotVec( constVectorArg v0, constVectorArg v1 )
{
asm("xxxx";
}

This topic is closed to new replies.

Advertisement