instantreality forum
news: Welcome to the instantreality forums!
 
*
Welcome, Guest. Please login or register.
Did you miss your activation email?
January 20, 2018, 12:21:12 am


Login with username, password and session length


Pages: [1]
  Print  
Author Topic: Using VRPN to get Tracker data/ IOTracker  (Read 6323 times)
rieberde
Newbie
*
Posts: 3


View Profile
« on: May 21, 2013, 09:06:36 pm »

Hello,
Iím currently working on a Project, and i got stuck.
I am trying to connect an IOTracker (http://www.iotracker.com/) to instant-reality using vrpn(http://www.cs.unc.edu/Research/vrpn/) and
the instant reality C++ API.
There I try creating a new  Node, that connects to a vrpn_server and push the values into instantreality.
My Problem is that the VRPN_CALLBACK functions  are never called, although I get a connection to the vrpn_server.

Has anyone here experience with instantreality combined with vrpn?

Or does anyone know another way to connect to the IOTracker to instant-reality?
Best wishes and thanks.
Logged
nwagg14
Newbie
*
Posts: 7


View Profile
« Reply #1 on: July 03, 2013, 08:42:41 pm »

I'm having this same issue where InstantReality can connect to the VRPN server, but the callbacks are never called. Is there any chance you've figured out a solution to this?
Logged
rieberde
Newbie
*
Posts: 3


View Profile
« Reply #2 on: July 04, 2013, 03:29:58 pm »

Hi, at least for my Problem I found a Solution:
You have to call the 'mainloop()'-function in separate Thread, at least this is what helped me.
Logged
nwagg14
Newbie
*
Posts: 7


View Profile
« Reply #3 on: July 09, 2013, 06:17:59 pm »

Do you mind giving me a hint how? I can't find any information on how to start a new thread in InstantReality.
Logged
tfranke
Administrator
Jr. Member
*****
Posts: 89


View Profile
« Reply #4 on: August 05, 2013, 09:31:55 am »

Hey guys,

I've been out of office the last two weeks. Do you have a code snippet I can take a look at? It's hard to judge what your problem is by the description you gave. I have no knowledge about VRPN, but I can help on the InstantIO side of things.

Cheers
Logged
nwagg14
Newbie
*
Posts: 7


View Profile
« Reply #5 on: August 05, 2013, 05:37:44 pm »

Sure.

I have a few things declared in my ZSpaceNode, including

Code:
static void VRPN_CALLBACK handle_button(void *userdata, const vrpn_BUTTONCB b);
static void VRPN_CALLBACK handle_tracker(void *userdata,const vrpn_TRACKERCB t);

vrpn_Tracker_Remote *tracker_;
vrpn_Button_Remote  *button_;

And here's my processData function:

Code:
int ZSpaceNode::processData()
{
    // ###ADDCODE###
    // Open/connect to you device
    // Send/receive data in the waitThread() loop
    // setState (NODE_ERROR) and return -1 on error

    bool deviceOpen = true;

     std::cerr << "ZSpace: Run processData\n" << std::endl;

    if (deviceOpen)
        setState(NODE_RUNNING);
    else
    {
        setState (NODE_ERROR);
        return -1;
    }

    // Important: you need to wall waitThread in every loop
    // time is in millisecond
    while (waitThread(10))
    {
tracker_->mainloop();
button_->mainloop();
    }

    // Thread finised
    setState (NODE_SLEEPING);

    std::cerr << "ZSpace: finish processData" << std::endl;

    return 0;
}

In theory, when the VRPN mainloop function is called, the corresponding callback function is called at some point. When I use this code inside of InstantReality however, the callback is never called. This seems like an error with VRPN, but my code works otherwise, and its clear that InstantReality is connected to my server. Here is some more information about VRPN clients.

Thanks!
Logged
tfranke
Administrator
Jr. Member
*****
Posts: 89


View Profile
« Reply #6 on: August 06, 2013, 02:20:56 pm »

So I usually do the following to have a thread running: I declare my class with a thread function and a Medusa::Thread object.

Code:
class MyNode : public Node
{
  ...
 
  Medusa::Thread *thread_;

  int thread();
}

In the initialization of the node (virtual void start()) I check if the node is already running, and if not call my init() function that initializes the device, then set the node state to "running" and create a thread.

Code:
void MyNode::start()
{
    // start thread to update images
    if (thread_->isRunning() == false)
    {
        init();

        if (getState() != NODE_ERROR)
        {
            // Start the thread
            setState(NODE_RUNNING);
            thread_->start();
        }
    }
}

In the thread I do all the polling, waiting or whatever needs to be done. In your case this might look like this:

Code:
int MyNode::thread()
{
    while (getState() == NODE_RUNNING)
    {
        tracker_->mainloop();
        button_->mainloop();
    }   

    return 0;
}

Please try this and see if it works.

Cheers
Logged
tfranke
Administrator
Jr. Member
*****
Posts: 89


View Profile
« Reply #7 on: August 06, 2013, 02:24:22 pm »

I've just noticed that these are two mainloops. Are they supposed to go into two separate threads?
Logged
nwagg14
Newbie
*
Posts: 7


View Profile
« Reply #8 on: August 06, 2013, 07:12:07 pm »

Ok so now I have:
Code:
class ZSPACENODE_DLLMAPPING ZSpaceNode : public ThreadedNode
{
    ...
static void VRPN_CALLBACK handle_button(void *userdata, const vrpn_BUTTONCB b);
        static void VRPN_CALLBACK handle_tracker(void *userdata,const vrpn_TRACKERCB t);

Medusa::Thread *thread_;
int thread();

vrpn_Tracker_Remote *tracker_;
vrpn_Button_Remote  *button_;
}

void ZSpaceNode::initialize()
{
        //init device, etc

if(thread_->isRunning() == false)
{
if(getState != NODE_ERROR)
{
setState(NODE_RUNNING);
thread_->start();
}
}
}

int ZSpaceNode::thread()
{
while(getState() == NODE_RUNNING)
{
tracker_->mainloop();
button_->mainloop();
}

return 0;
}

But this doesn't work at all. I can't find any information on how to actually initialize and use Medusa::Thread, and the only code I've found that mentions it is the declaration in ThreadedNode.h:

Code:
namespace Medusa
{
class Thread;
}

Am I missing something?
Logged
tfranke
Administrator
Jr. Member
*****
Posts: 89


View Profile
« Reply #9 on: August 07, 2013, 09:28:03 am »

Oh, sorry, totally forgot to include that line:

Code:
thread_ = new Medusa::ObjectThread<MyNode>(*this, &MyNode::thread);
Logged
nwagg14
Newbie
*
Posts: 7


View Profile
« Reply #10 on: August 07, 2013, 05:27:51 pm »

Oh, sorry, totally forgot to include that line:

Code:
thread_ = new Medusa::ObjectThread<MyNode>(*this, &MyNode::thread);

Right. But this doesn't work either because Medusa::Thread is never defined in my codebase, and Medusa::ObjectThread is never even declared.

So I either get
Code:
error C2039: 'ObjectThread' : is not a member of 'Medusa'
or
Code:
error C2512: 'Medusa::Thread' : no appropriate default constructor available
Logged
tfranke
Administrator
Jr. Member
*****
Posts: 89


View Profile
« Reply #11 on: August 08, 2013, 12:26:57 pm »

Please also include this header:

Code:
#include <Medusa/ObjectThread.h>
Logged
nwagg14
Newbie
*
Posts: 7


View Profile
« Reply #12 on: August 08, 2013, 05:31:52 pm »

Please also include this header:

Code:
#include <Medusa/ObjectThread.h>

Ok, so it looks like the real issue is that the Medusa headers aren't on my machine. They should be located in Instant Reality/Include right?

I've reinstalled both 2.2.0 and 2.3.0 32 bit versions for Windows and I still don't have that header...
Logged
tfranke
Administrator
Jr. Member
*****
Posts: 89


View Profile
« Reply #13 on: August 09, 2013, 09:57:13 am »

Ah right, these are only accessible in the SDK. Sorry about that. You may want to use your own threading mechanism (for instance Boost Thread). I have to see if we can include these headers in the regular release as well.
Logged
nwagg14
Newbie
*
Posts: 7


View Profile
« Reply #14 on: August 09, 2013, 06:28:12 pm »

Okay, thanks so much for your help!
Logged
Pages: [1]
  Print  
 
Jump to:  

Powered by SMF 1.1.15 | SMF © 2011, Simple Machines