Jump to content

Getting and setting Omega in Local space causes object rotation to go crazy


Recommended Posts

Pretty simple bug to duplicate, really. If you get an object's current Omega, and then set the Omega using that same value in Global space the object in question rotates as expected--at a constant speed.

 

However, if you try to do that same using the object's Local Space then the object's rotation quickly spins wildly out of control, with the Omega value flip-flopping from positive to negative.

 

Here's a simple test app you can try. Please excuse the less-than-elegant code, I'm in the middle of testing a few things and my brain-storming code is NOT pretty...

 

WASD will move the green square around. If it bumps into another surface, or if you add rotation with T and Y, the blue square's rotation goes nuts. However, if you change the GetOmega and SetOmega commands to TRUE (for global space) then everything works as expected...

 

ALSO, if you set to true and tap T or Y to start a rotation you'll see the cube eventually slow it's rotation until it stops. Obviously there's some form of drag going on (probably so the object can eventually go to sleep). Is there a way to alter this so an object rotates/moves indefinitely (as an object would in space)? If not I'll find a way to over ride that behavior, but a command to do it would be more elegant. (By the way, the object in question does not use gravity and is floating "in mid air", so surface to surface friction doesn't apply smile.png )

 

Thanks

 

#include "App.h"
using namespace Leadwerks;

App::App() : window(NULL), context(NULL), world(NULL), camera(NULL) {}
App::~App() { delete world; delete window; }
Pivot* Dummy;
Pivot* ROOTpiv;
Light* omnilight;
Model* Tsurface;
Model* elevator;
Model* character;
Shape* Cshape;
float hvalue = 0.6;
Vec3 horiforce = 0.0, ROTforce = 0.0;
Vec3 Turnit = 0.0;
Model* wallA;
Model* wallB;

bool App::Start()
{
window = Window::Create("test", 0, 0, 1024, 768, Window::Titlebar + Window::Center);
context = Context::Create(window);
world = World::Create();
camera = Camera::Create();
camera->SetRange(0.1, 200);
camera->SetPosition(0, 2, -5);
world->SetGravity(0, -100, 0);
Dummy = Pivot::Create();
omnilight = PointLight::Create();
omnilight->SetPosition(0, 10, -10);
omnilight->SetRange(20);
omnilight->SetShadowMapSize(1024);
Tsurface = Model::Box();

Tsurface->SetMass(20000000);
Tsurface->SetCollisionType(Collision::Scene);
Tsurface->SetColor(1.0, 0.0, 1.0);
Cshape = Shape::Box(0, 0, 0, 0, 0, 0, 1, 1, 1);
Tsurface->SetShape(Cshape);
Cshape->Release();
Tsurface->SetScale(20, 0.5, 20);
Tsurface->SetPosition(0, -2, 0);
Tsurface->SetFriction(0, 0);
Tsurface->SetGravityMode(0);
wallA = Model::Box();
wallA->SetScale(1, 1, 1);
wallA->SetMass(30);
//wallA->SetMass(0);
wallA->SetCollisionType(Collision::Prop);
wallA->SetColor(0.0, 1.0, 0.0);
Cshape = Shape::Box(0, 0, 0, 0, 0, 0, 1, 1, 1);
wallA->SetShape(Cshape);
Cshape->Release();
wallA->SetPosition(0, 0, 0);
wallA->SetGravityMode(0);

camera->SetParent(wallA);
wallB = Model::Box();
wallB->SetScale(1, 1, 1);
wallB->SetMass(30);
//wallB->SetMass(0);
wallB->SetCollisionType(Collision::Prop);
wallB->SetColor(0.0, 1.0, 1.0);
Cshape = Shape::Box(0, 0, 0, 0, 0, 0, 1, 1, 1);
wallB->SetShape(Cshape);
Cshape->Release();
wallB->SetPosition(2, 2, 2);
wallB->SetGravityMode(1);
wallB->SetScale(3, 3, 3);
return true;
}
bool App::Loop()
{
if (window->KeyDown(Key::Escape) || window->Closed()) return false;
Vec3 offset = 0.0;
Vec3 Roffset = 0.0;
Vec3 currOMG = 0.0;

offset = wallA->GetPosition(true);
Roffset = wallA->GetRotation(true);
currOMG = wallA->GetOmega(false); //<<<< CHANGE THIS TO TRUE FOR GLOBAL FOR CORRECT RESPONSE
std::cout << currOMG.y << "start" << endl;
wallA->PhysicsSetPosition(0, 0, 0, 0.5);
Dummy->SetPosition(0, 0, 0);
Dummy->SetRotation(Roffset, true);

if (window->KeyDown(Key::A)) Dummy->Move(0.01, 0, 0);
else if (window->KeyDown(Key:)) Dummy->Move(-0.01, 0, 0);
if (window->KeyDown(Key::W)) Dummy->Move(0.0, 0.0, -0.01);
else if (window->KeyDown(Key::S)) Dummy->Move(0.0, 0.0, 0.01);
if (window->KeyDown(Key::E)) Dummy->Move(0.0, -0.01, 0.0);
else if (window->KeyDown(Key::C)) Dummy->Move(0.0, 0.01, 0.0);
Turnit = 0.0;
if (window->KeyDown(Key::T)) Turnit.y += 0.100;
else if (window->KeyDown(Key::Y)) Turnit.y -= 0.100;
currOMG += Turnit;
Vec3 NewPOS = Dummy->GetPosition(true);
horiforce += (NewPOS + (offset * -1.0));
wallB->SetVelocity(horiforce);
Tsurface->SetVelocity(horiforce);
wallA->SetOmega(currOMG, false); //<<<< CHANGE THIS TO TRUE FOR GLOBAL FOR CORRECT RESPONSE
std::cout << currOMG.y << "end" << endl;
//Continue
Time::Update();
world->Update();
world->Render();
context->SetColor(255, 0, 0);
context->SetBlendMode(Blend::Alpha);
context->DrawText("UPS: " + String(Time::UPS()), 2, 2);
context->SetBlendMode(Blend::Solid);
context->SetColor(0, 0, 0);
context->Sync(false);
return true;
}

--"There is no spoon"

Link to comment
Share on other sites

Guest
This topic is now closed to further replies.
 Share

×
×
  • Create New...