Jump to content
  • Advertisement
Sign in to follow this  
JoakimNordstrandStien

Vector transformation

This topic is 2539 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

Greetings, GameDev community!

I'm currently working with Box2D, and I'm implementing an explosion-effect.

Therefore, I'm in need of a direction vector to be multiplied by the force (which is based on distance).

In order to make it appear as seamless as possile, I need to first transform the vector so that the highest value of the vector is 1. Let me show you;

A vector of (15, 10) would be (1, 6.67). As would a vector (30,15) be (1, 0.5).

Has anyone done this before and have a code snippet to share? The general theory / principle behind it would be sufficient as well.

Thanks in advance :)

//pimms

Share this post


Link to post
Share on other sites
Advertisement
Compute the maximum of the absolute values of the coordinates and divide every coordinate by it. Is that what you wanted?

Share this post


Link to post
Share on other sites
Thanks for the quick replies, guys. Appreciate it a lot :)

@alvaro
I'm not 100% sure of what you mean - what I've tried (without much success) is to first find the ratio between X and Y, based on the highest value.

If the highest value is > 1.0, I divide X and Y by the highest value. This produces some funny results, though.

If the highest value is < 1.0, I find the ratio by dividing 1 by the highest. Then X and Y is divided by ratio.

The current (faulty) code:
[source]
if ( vector.x > vector.y ) {
for (;;) {
if ( high < 1.0f ) {
ratio = 1.f / high;
x = high * ratio;
y = low * ratio;
break;
}
if ( high > 1.0f ) {
ratio = high / high;
x = high / ratio;
y = low / ratio;
break;
}
}
}
[/source]


@Hassanbasil
I've looked into normalizing the vector, but that would be quite the workaround for me, as I'm calculating the force to be applied as so;

[source]
body->ApplyForce( (hitVector*distance)*force, body->GetWorldCenter() );
[/source]

Where hitVector is the vector I'm trying to calculate.

Share this post


Link to post
Share on other sites
I came up with something that works somewhat decent, thought I'd share it as it might be of help to someone out there :) It's messy as shit, and could use a rewrite, but I'm satisfied considering it's 2:45 AM.

As mentioned, this function returns a vector scaled down to 1.

[source]
inline b2Vec2 scaleVecTo1( b2Vec2 vector ) {
//flag for reversing them to negative before return
bool invX=NO, invY=NO;

float x=0.f, y=0.f;
float ratio;

invX = vector.x < 0.f ? YES : NO;
invY = vector.y < 0.f ? YES : NO;
vector.x *= vector.x < 0.f ? -1.f : 1.f;
vector.y *= vector.y < 0.f ? -1.f : 1.f;

if ( vector.x > vector.y ) {
for (;;) {
if ( vector.x < 1.0f ) {
ratio = 1.f / vector.x;
x = vector.x * ratio;
y = vector.y * ratio;
break;
}
if ( vector.x > 1.0f ) {
ratio = vector.x / vector.x;
x = vector.x / ratio;
y = vector.y / ratio;
break;
}
}
}

if ( vector.x <= vector.y ) {
for (;;) {
if ( vector.y < 1.0f ) {
ratio = 1.f / vector.y;
y = vector.y * ratio;
x = vector.x * ratio;
break;
}
if ( vector.y > 1.0f ) {
ratio = vector.y / vector.y;
y = vector.y / ratio;
x = vector.x / ratio;
break;
}
}
}

x *= invX ? -1.f : 1.f;
y *= invY ? -1.f : 1.f;

return b2Vec2(x,y);
}
[/source]

Share this post


Link to post
Share on other sites

@alvaro
I'm not 100% sure of what you mean - what I've tried (without much success) is to first find the ratio between X and Y, based on the highest value.



I mean this:
inline b2Vec2 scaleVecTo1( b2Vec2 vector ) {
float m = std::max(std::abs(vector.x), std::abs(vector.y));
return b2Vec(vector.x/m, vector.y/m);
}


[font="Consolas,"] [/font]

Share this post


Link to post
Share on other sites
alvaro's method is just what you're asking for - but what you're asking for doesn't seem to be the right way to do it, normalizing the vector and making it a unit vector is actually what looks suitable in your case, since it has the length of 1 (hence the name unit vector)

let's assume you have the vector (5,10), your desired method will make it (0.5,1), now calculate the length of it: sqrt(0.5*0.5+1*1) = sqrt(1.25) != 1
now the normalization method: sqrt((5 / sqrt(5 * 5 + 10 * 10))^2 + (10 / sqrt(5 * 5 + 10 * 10))^2) = 1

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!