photo

How to apply collision or contactpoint to all parts of GeodeticPivot(Urgent)

Recommended Posts

Hello everyone ,

I want to get into the topic directly because it is an emergency.I recently added rigidbody to the relevant objects on the unigine editor side and I can see that the laser object touches other objects via these rigid bodies on the code side.But since I cannot add a rigid body to the geodetic pivota, I cannot detect the point where the object touches the earth.The process involved is just throwing a laser at one point and getting the coordinate from the point it touches.

The code that I access to the objects over the rigid size is below.I just want to implement the same process in the geodetic pivot(it should include all trees and all elements in geodetic pivot). But I don't know how I can do it.

//.CPP FILE
//mhtsMainreference is the node that have 5km rigidbody shape, it is simply laser and moves with its parent
mhtsMainreference->getObjectBodyRigid()->getBody()->addContactCallback(Unigine::MakeCallback(this,contact_callbackforhts));

//Basically i append all contact body points to callbackforhts Unigine::Vector , other requirments are available in header file which is available below
callbacksforhts.append(new ContactArgumentsforhts(body,num));
mmissilehtstargetpoint =  body->getContactPoint(num); //it returns me to contacted point of each objects
//HEADER FILE FOR CALLBACK
 //Collision callback for hts
    struct ContactArgumentsforhts
        {
            Unigine::BodyPtr body;
            int num;

            ContactArgumentsforhts(const Unigine::BodyPtr &body, int num)
            {
                this->body = body;
                this->num = num;

            }
        };

    void contact_callbackforhts(Unigine::BodyPtr body, int num);
    Unigine::Vector<ContactArgumentsforhts*> callbacksforhts;

Laser object editor is available below

Laser.thumb.png.8d0cae5efa2a6fe8eb22d7938bccf9c6.png

As you see there is no physics on geodeticpivot, so above code does not work with it.

1597862368_geodeticpivot.thumb.png.b92cc8510c12dc2d0fb35d00de35acf1.png

 

We have really limited time to implement this laser geodeticpivot(trees,ground so on) interaction.Please help me for this

Thank you.

Edited by burakdogancay

Share this post


Link to post

Hello,

To imitate laser ray you don't need physics. Intersection ray is enough.

Here's the article that explains intersections in Unigine: https://developer.unigine.com/en/docs/2.8/code/usage/intersections/index

You need World::getIntersection method. For the terrain you might need force intersection flag

You can find examples in UnigineScript samples (intersection_00) and the article mentioned above. There's also a laser ray example in the VR Sample.

Thanks.

Share this post


Link to post

First of all thank you for your response and interest, we apreciate it.So, According to your answer i wrote below function for intersection

void loop(){
getintersection();
}

void Bites::Sim::BSTA::getintersection()
{
    BTerrainManager *tTerrainManager = BTerrainManager::instance();//This class gets terrain features and also set flags for getting intersection

    Unigine::Math::Vec3 tRayPos = mhtsMainreference->getWorldPosition();
    Unigine::Math::Vec3 tRayDir = Unigine::Math::Vec3(1,0,0); //gets laser X direction, which is correct one
    Unigine::Math::vec3 tResult;
    Unigine::Math::vec3 tNormal;

    /// 20km calculation

    Unigine::Math::vec3 tP0(tRayPos);
    Unigine::Math::vec3 tP1(tRayPos + tRayDir*20000.0);
    if(tTerrainManager->getIntersection(tP0, tP1, &tResult, &tNormal)){//this function is available below code

    if(mListener->gimbalRx().laserStatus == 1){
       BMissileManager::instance()->uparameters.mmissilehtstargetpoint = mmissilehtstargetpoint;
       BMissileManager::instance()->parameters.mmissilehtstargetpoint = missilecalchtsdist();
       BMachineGunManager::instance()->parameters.mHtsTargetPoint    = missilecalchtsdist();
       BMissileManager::instance()->parameters.mInitialHtsPnt=missilecalchtsdist();
        mGimbalTx->laserdistance = static_cast<qint16>(tResult.x);
        qDebug()<<"LASER STATUS : "<<mGimbalTx->laserdistance;

    }
    }
    else{
    BMissileManager::instance()->parameters.mmissilehtstargetpoint = 0;
    BMachineGunManager::instance()->parameters.mHtsTargetPoint    =0;
    BMissileManager::instance()->parameters.mInitialHtsPnt=0;
    BMissileManager::instance()->uparameters.mmissilehtstargetpoint = Unigine::Math::Vec3(0,0,0);}
}
          
bool BTerrainManager::getIntersection(Unigine::Math::vec3 p0, Unigine::Math::vec3 p1, Unigine::Math::vec3 *ret, Unigine::Math::vec3 *norm)
{

    if(!mReady)
        return false;

    Unigine::Math::vec4 texcoord;
    int index = 0;
    int surface = 0;
    mTerrain->setForceIntersection(1);
    int tResult = mTerrain->getIntersection(p0, p1, ret, norm, &texcoord, &index, surface);
    mTerrain->setForceIntersection(0);

    return tResult != 0;
}

It worked but returned wrong coordinate.For example, i directed laser to the sky but it returned a  coordinate(i think it should not).Also it returns wrong coordinate when i direct to the object.But contact call point return with correct contacted coordinate point.

 

We are close to solve it, but need more help please.

Edited by burakdogancay

Share this post


Link to post

Now you need to translate world coordinates into geographic. 


//For curved terrain
geopivot->toGeodetic(translate(world_pos));

//For flat terrain
geopivot->mapFlatToGeodetic(world_pos + Vec3(0, 0, geopivot->getOrigin().z));

 

Share this post


Link to post

Thank you so much, we solved it with your help.so ı would li̇ke to share full code to help other peoples for i̇ntersecti̇on of each object and envi̇ronment

void loop(){  //it should be your main loop
  getintersection()
}

BSTA::getintersection()
{
    BTerrainManager *tTerrainManager = BTerrainManager::instance();

    Unigine::Math::Vec3 tRayPos = mhtsSecondreference->getWorldPosition();
    Unigine::Math::Vec3 tRayDir = Unigine::Math::Vec3(mhtsSecondreference->getWorldDirection(Unigine::Math::AXIS_X));
    Unigine::Math::vec3 tResult;
    Unigine::Math::vec3 tNormal;

    /// 20km away calc

    Unigine::Math::vec3 tP0(tRayPos);
    Unigine::Math::vec3 tP1(tRayPos + tRayDir*20000.0);
    if(tTerrainManager->getIntersection(tP0, tP1, &tResult, &tNormal)){
        qDebug()<<"LASER STATUS : "<<mListener->gimbalRx().laserStatus;
        if(mListener->gimbalRx().laserStatus == 1){
            BMissileManager::instance()->uparameters.mmissilehtstargetpoint = mmissilehtstargetpoint;
            BMissileManager::instance()->parameters.mmissilehtstargetpoint = missilecalchtsdist();
            BMachineGunManager::instance()->parameters.mHtsTargetPoint    = missilecalchtsdist();
           BMissileManager::instance()->parameters.mInitialHtsPnt=missilecalchtsdist();

            //            if(tResult.x<0 && tResult.y <0){


            mGimbalTx->laserdistance = static_cast<qint16>(clcLaserDistance(((mBody->getWorldPosition().x*-1) + tResult.x),((mBody->getWorldPosition().y*-1)+tResult.y))); //We can get correct distance with this tiny calculation


            qDebug()<<"LASER DISTANCE : "<<tResult.x<<mBody->getWorldPosition().x<<mGimbalTx->laserdistance;
        }
    }
    else{
        qDebug()<<"LASER DISTANCE ELSE SITUATION : "<<mGimbalTx->laserdistance;
        BMissileManager::instance()->parameters.mmissilehtstargetpoint = 0;
        BMachineGunManager::instance()->parameters.mHtsTargetPoint    =0;
        BMissileManager::instance()->parameters.mInitialHtsPnt=0;
        BMissileManager::instance()->uparameters.mmissilehtstargetpoint = Unigine::Math::Vec3(0,0,0);}
}
BTerrainManager::getIntersection(Unigine::Math::vec3 p0, Unigine::Math::vec3 p1, Unigine::Math::vec3 *ret, Unigine::Math::vec3 *norm)
{

    if(!mReady)
        return false;

    Unigine::Math::vec4 texcoord;
    int index = 0;
    int surface = 0;
    mTerrain->setForceIntersection(1);
    int tResult = mTerrain->getIntersection(p0, p1, ret, norm, &texcoord, &index, surface);
    mTerrain->setForceIntersection(0);

    return tResult != 0;
}
BSTA::clcLaserDistance(const double pPointX, const double pPointY)
{
    Unigine::Math::vec3 tDistanceVec;
    double tDistance = sqrt(pow(pPointX,2)+pow(pPointY,2));

    return tDistance;

}

 

Edited by burakdogancay
  • Like 1

Share this post


Link to post

Ah, i forgot to mention about one thing.It is not detecting any tree with this code.

Could you please direct me to solve this problem?

Thank you in advance

Share this post


Link to post

What is a tree? Which object you're using for trees? ObjectGrass or MeshClutter? Or both?

Share this post


Link to post

Trees are created as ObjectMeshClutter

Share this post


Link to post

Just revised your code.

Are you sure you've used World::getIntersection? Terrain uses its own intersection, other objects will work with World::getIntersection, as I wrote in the first message.

Also, if the MeshClutter is not visible when you cast a ray you need to create an invisible LOD with Visibility distance = 0 and configured viewport mask.

Share this post


Link to post