ROS Resources: Documentation | Support | Discussion Forum | Index | Service Status | ros @ Robotics Stack Exchange
Ask Your Question

Nishant's profile - activity

2016-08-03 08:09:07 -0500 received badge  Great Question (source)
2016-02-13 15:33:36 -0500 received badge  Nice Question (source)
2015-12-07 00:59:14 -0500 received badge  Good Question (source)
2015-09-22 08:29:06 -0500 received badge  Nice Question (source)
2014-10-06 15:46:46 -0500 received badge  Notable Question (source)
2014-10-06 15:46:46 -0500 received badge  Famous Question (source)
2014-10-03 18:02:28 -0500 received badge  Famous Question (source)
2014-08-26 02:23:47 -0500 received badge  Famous Question (source)
2014-04-20 06:51:45 -0500 marked best answer Publishing and subscribing to a topic in different threads

Hi all!

I was just curious about this, before I actually sit for coding.

Suppose I have a thread in which I am publishing to a topic. Then, can I subscribe to that same topic from some different thread?

I am really sorry if this question is too trivial. I just don't want to end up writing code for nothing :)

All help is appreciated!

2014-04-20 06:51:02 -0500 marked best answer Intermittent subscription to a topic with/without timer possible?

Hello,

It is really important for me to know this before I start any coding. Here is what I want:

1) A continuous stream of data is being published as a topic. (At frequency >= 50Hz).

2) I want to read from this stream, and write the data to a text file when a parameter in the parameter server is set. Whenever I take readings from the stream, I want data to be written to the file at 50Hz (this frequency is important. Cannot reduce this).

I made a node which is dedicated to publishing the topic for this data. I then tried subscribing to it at different time intervals. IT DOES NOT WORK. I got numerous suggestions from you guys (for which I am really thankful), but I am still stuck with my problem. I basically want to tap into the topic whenever I want, read data and write it to a text file, and then leave reading the topic till the next time I feel like writing to the file again. Never thought it would be so hard.

Anyway, I tried using [ delays (sleep(n) commands) and spinOnce() ] combinations in while loops but that did not work as well. I have a question here:

--> Does that mean, that a subscriber in ROS HAS to CONTINUOUSLY listen to the topic being published? What if I don't want to? What if I want to listen to a topic say, only when 'flag' is set to 1?

I then stumbled upon timers. Timers basically take a callback function, and execute that function every T seconds (where T is the time period). A clever way to publish a topic is then to use the publish() command in the timer callback. An even more clever way to exploit this structure, is to declare the callback function as a member function of your node class [ I got the above two 'clever ideas' from people who helped me out in previous related questions asked by me. Thanks!]. I have a question here:

--> What if my timer has time period say, 0.2 seconds, and my callback function requires 0.3 seconds to execute? What happens then? Is there some sort of queue where timer callbacks are lined up?

I am sorry if I am repeating stuff from previous questions, or if my questions sound too basic. It just bothers me that ROS being such an amazing platform, does not seem to have a simple solution to intermittent/'at will' subscription to a topic!

All help is greatly appreciated. Thank you for the patience to go through this post!

2014-04-20 06:51:00 -0500 marked best answer Subscriber node not working for topic at 50Hz

Hello all,

So I have a topic published by a publisher node, at 50 Hz. The topic publishes a message 'loadMsg' which consists of the following data types

1) string unit

2) float64 load

Now I have my subscriber node, which is the following piece of code

#include <ros/ros.h>
#include <robot_comm/robot_comm.h>
#include "std_msgs/String.h"
#include "cell_node/loadMsg.h"


void loadSensor(const cell_node::loadMsg &d)
{
  ROS_INFO("Load Unit = [%s] , Value = [%lf] ", d.unit.c_str(),d.load);
}



int main(int argc, char** argv)
{
  ros::init(argc, argv, "demo");
  //FILE * pFile;

  ros::NodeHandle n;

  ros::Subscriber sub = n.subscribe("loadSensor", 1000, loadSensor);
  //ros::Rate loop_rate(50);
int i = 0;
while(i<10)
{
  usleep(20000);
  ros::spinOnce();
  i++;
}
  //pFile = fopen ( "myfile.txt" , "w+" );
  //fwrite (buffer , 1 , sizeof(buffer) , pFile );
  //fclose (pFile);

return 0;
}

So what this should do is basically sample from the stream of 'loadMsg' data being published at 50Hz. And the sampling should happen again at 50Hz (1/20000usec).

However, I am not getting any output! rosmake/make work perfectly, without any errors. When I run the node however, I get nothing.

What may be going wrong? In an earlier post, I asked a similar question. But it worked then, it refuses to work now. Here is the link to that:

http://answers.ros.org/question/38131/rosspinonce-not-functioning-properly/

Also, if I replace ros::spinOnce() by ros::spin() and remove the while loop, then it does sample from the topic, but seemingly at a lesser frequency.

All help is greatly appreciated!

2014-04-20 06:51:00 -0500 marked best answer How can I add a dependency after I have created a package?

Hi all,

I created a package called demo. It has two dependencies

1) roscpp

2) robot_comm

Now I want to interface it with a sensor, so I created a node called 'cell_node' for the sensor. I plan to use information from a topic in 'cell_node' which publishes the message 'loadMsg' at 50Hz.

But then, I am getting an error

cell_node/loadMsg.h : No such file or directory.

I kind of know why this is happening. It is because I never added cell_node to the list of dependencies when I first created my package demo.

My question is, how can I add a new dependency to an already existing package, so that it compiles code in that dependency too?

Thanks! All help is appreciated :)

2014-04-20 06:50:59 -0500 marked best answer What type of messages can be used in services?(existing and custom)

Hello!

I was just curious about what kind of messages I can transmit over services and topics. Is there a list available somewhere which I can refer to for this? I know that simple messages can be of the following types

1)a built-in type, such as "float32 pan" or "string name"

2)names of Message descriptions defined on their own, such as "geometry_msgs/PoseStamped"

3)fixed- or variable-length arrays (lists) of the above, such as "float32[] ranges" or "Point32[10] points"

4)the special Header type, which maps to std_msgs/Header

Also, what if I want to pass my own class instance as a message? What do I need to do that?

All help is greatly appreciated. Thanks!

2014-04-20 06:50:59 -0500 marked best answer ros::spinOnce() not functioning properly

Hello,

So I went through the tutorials for publishing/subscribing for a message over a ROS topic over here

http://ros.org/wiki/ROS/Tutorials/WritingPublisherSubscriber%28c%2B%2B%29

So, I ran everything as they told me to in the tutorial, and it worked fine. I was able to see the output at 10Hz being published and subscribed to. Then I decided to tinker around with the subscriber code.

In that, I changed

// %Tag(SUBSCRIBER)%
  ros::Subscriber sub = n.subscribe("chatter", 1000, chatterCallback);
// %EndTag(SUBSCRIBER)%

  /**
   * ros::spin() will enter a loop, pumping callbacks.  With this version, all
   * callbacks will be called from within this thread (the main one).  ros::spin()
   * will exit when Ctrl-C is pressed, or the node is shutdown by the master.
   */
// %Tag(SPIN)%
  ros::spin();
// %EndTag(SPIN)%

to

int i=0;
while(i<50)
{
 // %Tag(SUBSCRIBER)%
  ros::Subscriber sub = n.subscribe("chatter", 1000, chatterCallback);
// %EndTag(SUBSCRIBER)%

  /**
   * ros::spin() will enter a loop, pumping callbacks.  With this version, all
   * callbacks will be called from within this thread (the main one).  ros::spin()
   * will exit when Ctrl-C is pressed, or the node is shutdown by the master.
   */
i++;
// %Tag(SPIN)%
  ros::spinOnce();
}
// %EndTag(SPIN)%

So this should print out "hello world xyz" 50 times right? However, it is not printing anything. As soon as I run this, the program runs as if there were no subscription and callback.

The callback function is the same as the one in the tutorial. No change there.

What then am I doing wrong regarding the spinning? Any help is greatly appreciated.

Thanks!

2014-04-20 06:50:59 -0500 marked best answer How to subscribe to a topic at will/on demand?

Hello all.

As indicated by the quick response of catagay and Lorenz to my previous question here

http://answers.ros.org/question/38088/how-do-i-create-a-ros-topic-publishersubscriber/

I started reading up on how to create publishing and subscribing agents, on the ros tutorials page.

http://www.ros.org/wiki/ROS/Tutorials/WritingPublisherSubscriber%28c%2B%2B%29

Here is what I understood from the tutorial:

1) The publisher in the example keeps on publishing forever.

2) advertise<std_msgs::string>() is the harbinger of the topic to be published. So this step seems necessary.

3) chatter_pub.publish(msg) is the guy who does the talking. Since he is in a while(ros::ok()), this will publish forever.

4) The subscriber also keeps on subscribing forever.

5) ros::Subscriber sub = n.subscribe("chatter", 1000, chatterCallback); tells the master to subscribe to the topic and call chatterCallback whenever there is a new message. Because of ros::spin(), however, this subscriber will continue listening to the topic and printing to the screen forever (till node dies, of course).

Based on these points, here are my related questions:

1) Is my understanding enumerated in the points above right? Or am I missing something?

2) What do you mean by "..call chatterCallback whenever there is a new message."? What does new message mean here? Does it mean that the function is called whenever the message on the topic is updated?

3) Suppose the publisher wants to keep on publishing the topic forever, but the subscriber wants to get messages from the topic only at select locations in my code. Say I want the subscriber to listen to a topic, extract a string from the message, convert it to an integer using atoi() and then print to screen. But I want it to do this in a for loop, while a particular condition in it holds. Is this possible?

4) Can I pass more arguments to the chatterCallback function? say instead of

void chatterCallback(const std_msgs::String::ConstPtr& msg);

I want it to be

void chatterCallback(const std_msgs::String::ConstPtr& msg, int &i, char c);

Is this possible? If yes, what changes do I need to reflect in the argument for the callback function for subscribe()?

5)I ask the above question (4) because I want some way, in which I can bring the result of all that I do in my callback function, into my main() function. Is there a way in which I can do this?

6)In the ROS tutorial I described above, there are the following few lines which escape my understanding. Any idea as to what they mean?

The message is passed in a boost shared_ptr, which means you can store it off if you want, without worrying about it getting deleted underneath you, and without copying the underlying data.

I somehow feel the above lines are related to my questions (4) and (5) above.

7) What happens if I don't use ros::spin() at all, in my subscriber code? Does that mean that the ... (more)

2014-04-20 06:50:59 -0500 marked best answer How do I create a ROS topic publisher/subscriber?

Hi all!

I have a sensor from which I read data via a serial communication (port is of type ttyUSB). Now I am thinking of writing two packages, "publisher_node" and "client". What I want is, publisher_node should read data from the sensor continuously, and publish it as a topic (basically just scream out the values). On the other end, in the client package, I have a specific task, during which I want to poll the device for readings.

I think that using a topic rather than a service is much more logical here. Data flow is a unidirectional stream. Its sort of like filling a cup(client) with water from a river(publisher_node). Am I thinking in the right direction?

My System: Ubuntu 11.10 64-bit

ROS version: ROS electric

Here are some of the key questions I have:

1) How do I create a topic for publisher_node? Is there any tutorial online for that? Maybe any step by step procedure..?

2) Once I know how to create a topic, I will do that in publisher_node. Then I will 'rosmake' and 'rosrun publisher_node publisher_node'. After that, I will make sure I have the topic up, by doing 'rostopic list'. All is OK. Now how do I write code/make the client "subscribe" to the topic? Any guidelines here?

3) Also, since this is serial communication, I want a special functionality with the topic. I want the user to have an option of setting the frequency of publishing (i.e how fast the data is screamed out). Is this possible with ROS?

Note: Yes, I am using a serial device, but I have not used rosserial in any way. I am implementing my own serial port by using the termios API in Linux.

Any help is greatly appreciated. Thanks in advance!

2014-04-20 06:50:50 -0500 marked best answer rosrun Error even when package compiles successfully

Hi all! As seen from my previous posts, its been only about a month since I started using ROS. So pardon me if I am making any newbie error here.

I am trying to run a node on ros, but I am unable to do so. Here are the details:

package name: robot_node

ros version: ROS electric

Ubuntu version: Ubuntu Oneiric 32-bit

1) I opened a terminal and said

roscore

2) I went to the folder of the package and said rosmake

roscd robot_node

rosmake

This works perfectly fine. I am able to compile with 0 failures.

3) My executable is called 'robot_node.cpp' so I do the following

rosrun robot_node robot_node

And then, I get this 'error':

[rosrun] Couldn't find executable named robot_node below ~/ros_workspace/ROS/robot_node [rosrun] Found the following, but they're either not files, [rosrun] or not executable: [rosrun] ~/ros_workspace/ROS/robot_node

There are a few things you should know that I already tried. These are

1) I checked the CMakeLists.txt for the package, and it does have the add_executable line.

2)I compiled all the first dependencies of the package separately, and they all compiled perfectly with 0 failures.

3) robot_node.cpp does have a int main() routine. :P

Any kind of help is greatly appreciated. Thanks for your time!

2014-04-20 06:50:43 -0500 marked best answer Creating own service (not copying from some other package)

Hi!

So I am new to ROS and I went through most of the beginner tutorials. I am at the point where I am learning how to create my own services. In the ROS tutorial on the link below, they tell you how to copy a service from some other package, using 'roscp'.

http://www.ros.org/wiki/ROS/Tutorials/CreatingMsgAndSrv#Creating_a_srv

A few questions come to mind after following the tutorial on the link above, and the subsequent 2-3 tutorials:

1) How do I create my OWN service? This tutorial shows how to copy one from some other package. Any steps that I can follow to create my own service with my own choice of messages?

2) Can anyone tell me how the client-server model works with the services? Its hard to understand what's going on without namespaces in the tutorial. A step-by-step description of what exactly is going on, would be really helpful.

3) This is not an essential piece of knowledge, but I am just curious about why there exist two commands rosservice and rossrv. Can't the functionality of both these commands be captured into one, say 'rosservice' only?

4) In the tutorial link above, they use the function advertiseService() with the nodehandle pointer. Is this a new addition to ROS? I remember seeing something like advertise() which does the same thing as advertiseService() on some other tutorial page.

Thanks for the patience to go through my post!

Nishant.

2014-01-28 17:30:24 -0500 marked best answer Connection Timed Out Error during setup keys installation

Hi there! I am new to ROS, and I need a little help here with installing ROS on my Ubuntu. I am running Ubuntu as a virtual OS in Windows 7 using VMware Player. Here are some details regarding the software.

Ubuntu version: Ubuntu 12.04 (Precise) 32-bit

ROS version: ROS fuerte

So I followed the step by step procedure for installing fuerte as given here

http://www.ros.org/wiki/fuerte/Installation/Ubuntu

But when I try to install step number 3 (setup your keys), the connection fails and I get a "Connection timed out. Could not connect to packages.ros.org" error. And then it keeps on trying to connect (which may be because of wget command) but always fails. I am using an Ethernet LAN cable connection for the internet, and the weird part is that I am connected to the net all the while that I am getting this error. I then tried the following, which again is never able to complete (Gets stuck at 0%)

sudo apt-get install update

What may possibly be wrong here? Any kind of help is greatly appreciated!

Thanks!

Nishant.

2014-01-28 17:29:42 -0500 marked best answer How can I create my own ROS C++ library?

Hello All,

This might be a repeat question (although I checked out some of the recommendations that ROS Answers asked me to look at while typing the title of this question, but they didn't seem relevant). Here goes.

So I have a C++ header file called "force_torque.h" (I had issues with this, but thanks to @jbohren I was able to fix those) and I want to convert it into a ROS library. So basically, I want it to be a valid ROS package, yet I also want other ROS packages to be able to depend on this package. So far, I have just been able to create a new package using 'roscreate-pkg'. Now I have a feeling that I need to modify "CMakeLists.txt" somehow, but I don't know how. Is there any good ROS tutorial on how to do this? Or if it could be described here on this question below, I would be very grateful.

Thanks, and all help is greatly appreciated!

Nishant

2014-01-28 17:29:40 -0500 marked best answer How do I get out of ros::spin() in another thread?

Hi All,

So what I am doing is enumerated in the points below. After that, I explain my questions in detail.

1) I recently got my hands on an ATI force/torque sensor which is pretty cool. I already had code which publishes the (fx,fy,fz,tx,ty,tz) readings from this sensor on the ROS network.

2) My job is to write the subscriber. The subscriber should have the following functionality:

2.a) I should be able to move around with the subscriber code. This means I want it to be preferably in the form of a single header file or something of the likes.

2.b) I want it to have a start_recording() functionality and stop_recording() functionality. These two functions essentially allow me to log the force/torque data to a text file, and stop the logging.

2.c) I want the data logging to be really fast. The more data I collect, the better for my application. The sensor itself publishes at 33 Hz, so anything in that ballpark is good for me.

3) So what I did was wrote a class called ForceTorqueObject which has some private threaded stuff going on, and some interface functions to allow the user to log/stop-log the data. Here is the class declaration.

class ForceTorqueObject
{
  private:
         volatile bool recording;
         pthread_t ft_sensor_thread;
         pthread_mutex_t ft_log_mutex;
         pthread_attr_t ft_attr;
         ros::NodeHandle *nh;
         FILE *ft_curr_logfile;
         ros::Subscriber ft_listener;
         queue<robot_comm::robot_ForceLog> ft_q; //shared object

         static void *ft_subscribe_main(void *args)
         {
           cout<<"Welcome to subscriber thread..."<<endl;
           ForceTorqueObject *ft_sensor = (ForceTorqueObject *)args;

           ft_sensor->ft_subscribe();
           cout<<"End of subscriber thread..."<<endl;
           pthread_exit(NULL);
           //return((void *)0);
         }
         void ft_subscribe();
         void ft_sensor_callback(const robot_comm::robot_ForceLog &fLog);
         void ft_queue_dump();

  public:
        ForceTorqueObject(ros::NodeHandle *n); //Constructor
        ~ForceTorqueObject();

        //User functions
        void ft_start_recording(const char *fLogFile);
        void ft_stop_recording();
        void ft_force_exit();
};

4) As seen from above, I am first creating a subscription thread, in which I have a callback function which checks for a flag "recording". Accordingly, it pumps the rosmsg carrying the force/torque data into a queue. ft_start_recording() just sets "recording" to 1, while ft_stop_recording() sets "recording" to 0, and dumps all contents of the queue into a text file. Thus I get my desired "log/stop-log" functionality.

5) In the separate thread for subscribing to the topic, I am calling ros::spin() from the ForceTorqueObject::ft_subscribe() function.

All this brings me to my set of questions:

1) How do I get out of the ros::spin() in the recording thread!? I wrote a small main() function to test my new class, and found out that once I am done logging and stop-logging, the subscriber thread still continues to live! I then realized that I could just not think of a way in which I can shut down the subscriber thread from the main thread.

2) So I tried changing things a little bit here-and-there. I tried doing

     static void *ft_subscribe_main(void *args)
     {
       cout<<"Welcome to subscriber thread..."<<endl;
       ForceTorqueObject *ft_sensor = (ForceTorqueObject *)args;
       while(ros::ok())
       {
         ft_sensor->ft_subscribe();
         ros::spinOnce();
       }
       cout<<"End of ...
(more)
2014-01-28 17:28:38 -0500 marked best answer Serial Load Cell is slow in ROS

Hi all,

So I have these load cells (4 of them) for which I have written a nice C++ class wrapper to interface with the sensors in a ROS environment. I have 4 topics, called "loadSensorX" where X = 0,1,2,3. These topics publish the force felt by these sensors in millipounds.

Now the load cells are actually LoadStar Sensor capacitive sensors with serial USB output. Here is the link to it

http://www.loadstarsensors.com/lc003-iload-tr-series-tilt-resistant-usb-load-cell.html

To the left of the page, you can see that default data rate for a standard sensor is 150 Hz. I have 4 of these sensors connected to my PC with a USB hub. Now all the topics and everything work fine. But when I do

rostopic hz /loadSensor0

instead of getting 150 Hz, I get only about 10-15 Hz. Also, when I connect just a single load cell instead of all 4 and try

rostopic hz /loadSensor0

I get about 50-55 Hz.

In both cases, I get much less data output rate compared to the promised 150 Hz. Which brings me to my question. Why does this happen? Is it because I am using a USB hub? Or is it my laptop specifications? Or is it ROS using up a lot of CPU power for just publishing 4 topics? Also, why do multiple load cells being connected with the hub affect my data rate?

My laptop specifications are

Intel Pentium CPU B960 Processor @ 2.20 GHz

64-bit Windows 8 OS with 32-bit Ubuntu 12.04 on VMWare Player.

4 GB RAM for host OS, 1 GB RAM for Ubuntu 12.04.

Thanks and any help is greatly appreciated.

2014-01-28 17:27:27 -0500 marked best answer Requesting different services with the same client node

Hi all!

So I have a ROS client like thus

ros::ServiceClient client

I also have two services:

1) "start_load_recording": This service basically tells a sensor to start logging force data into a text file. The type of message conveyed over this service is 'startMsg'

2) "stop_load_recording": This service tells that very same sensor to stop logging the force data, and close down the text file. The type of message conveyed over this service is 'stopMsg'

The thing is, I want to have a client which can request both these services. Thus I am using the client as a sort of 'on-off switch' for logging and un-logging the force data.

Can I do that? For example,

client = n.serviceClient<cell_node::startMsg>("start_load_recording");
//prepare my service message request variables. Lets say its called strt
client.call(strt);
.
.
.
//few lines of code
.
.
.
client = n.serviceClient<cell_node::stopMsg>("stop_load_recording");
//prepare my service message request variables. Lets say its called stop
client.call(stop);

Can I do the above?

Thanks and all help is greatly appreciated!