【笔记】ROSjava-android控制ROS机器人——ROSjava消息发送的解密

通过前面一篇Android上ROS开发——android_core创建一个android应用 应该已经懂了怎么把消息发布给某主题,但是由于发送消息的格式不同,代码有些许改动。虽然通过eclipse可以自己琢磨出如何处理某消息格式下的数据,或者直接google ROS的格式,但是找起来还是有点麻烦,我这还是详细讲解下。

首先是最基本最简单的发送std_msg格式:

package rosjava.wtf.pocketsphinx.version1;

import org.ros.concurrent.CancellableLoop;
import org.ros.namespace.GraphName;
import org.ros.node.AbstractNodeMain;
import org.ros.node.ConnectedNode;
import org.ros.node.topic.Publisher;

public class TalkChnString extends AbstractNodeMain {

	  
  @Override
  public GraphName getDefaultNodeName() {
    return GraphName.of("rosjava_tutorial_pubsub/talkerchnstring");
  }

  @Override
  public void onStart(final ConnectedNode connectedNode) {
    final Publisher<std_msgs.String> publisher =
        connectedNode.newPublisher("chatter", std_msgs.String._TYPE);
    // This CancellableLoop will be canceled automatically when the node shuts
    // down.
    connectedNode.executeCancellableLoop(new CancellableLoop() {
    	
      @Override
      protected void setup() {
      }

      @Override
      public void loop() throws InterruptedException {
          std_msgs.String chnstr = publisher.newMessage();
        chnstr.setData( IsrActivity.tmpchnstring );
        if(PocketSphinxROS.sendchnstring)
        {
        publisher.publish(chnstr);
      PocketSphinxROS.sendchnstring = false;
        }
       Thread.sleep(500);
      }
    });
  }
}
这里可以看出,我们取出IsrAcitivity.tmpchnstring中的字符串,通过PocketSphinxROS.sendchnstring控制单次发布给chatter主题。

package rosjava.wtf.pocketsphinx.version1;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

import org.ros.concurrent.CancellableLoop;
import org.ros.namespace.GraphName;
import org.ros.node.AbstractNodeMain;
import org.ros.node.ConnectedNode;
import org.ros.node.topic.Publisher;

import android.R.string;

import sensor_msgs.JointState;

public class TalkServo extends AbstractNodeMain {
	
	public static double[] vel= {0.5,0.5};
	public static double[] pos= {-0.17,0.75};

    String[] s = {"pan","tilz"}; 
    ArrayList<String> list = new ArrayList<String>(Arrays.asList(s));
    
  @Override
  public GraphName getDefaultNodeName() {
    return GraphName.of("rosjava_tutorial_pubsub/talkerserver");
  }

  @Override
  public void onStart(final ConnectedNode connectedNode) {
	  final Publisher<JointState> publisher =
		       connectedNode.newPublisher("joint_states", "sensor_msgs/JointState");
    // This CancellableLoop will be canceled automatically when the node shuts
    // down.
    connectedNode.executeCancellableLoop(new CancellableLoop() {
    	
      @Override
      protected void setup() {
      }

      @Override
      public void loop() throws InterruptedException {
    		JointState joint = (JointState) publisher.newMessage();
        if(PocketSphinxROS.sendservo)
        {
        	joint.setName(list);
        	joint.setVelocity(vel);
        	joint.setPosition(pos);
        	publisher.publish(joint);
        }
       Thread.sleep(100);
      }
    });
  }
}
这篇代码发送控制舵机信息到joint_states主题,重点来说明下舵机信息sensor_msgs/JointState的格式。官方说明该消息的格式是:
Header header

string[] name
float64[] position
float64[] velocity
float64[] effor


name就是舵机名,position就是舵机需要运动到的位置,velocity是舵机运动的速度,本质就是控制运动延迟。3个以数组形式一一对应,比如上面代码所示,舵机pan对应速度0.5,姿态-0.17。这样我们就可以通过处理这3个数据(这里是list,vel,pos)发送控制舵机的命令了。要说明的是这里和PC上ROS C++开发不一样,name需要放到ArrayList<String>中。

package rosjava.wtf.pocketsphinx.version1;

import geometry_msgs.Twist;
import org.ros.concurrent.CancellableLoop;
import org.ros.namespace.GraphName;
import org.ros.node.AbstractNodeMain;
import org.ros.node.ConnectedNode;
import org.ros.node.topic.Publisher;

public class TalkParam extends AbstractNodeMain {

	  public static String tmpstring="WTF";
	  public static float LX,LY,LZ,AX,AY,AZ;
	  
  @Override
  public GraphName getDefaultNodeName() {
    return GraphName.of("rosjava_tutorial_pubsub/talker");
  }

  @Override
  public void onStart(final ConnectedNode connectedNode) {
	  final Publisher<Twist> publisher =
		       connectedNode.newPublisher("cmd_vel", "geometry_msgs/Twist");
    // This CancellableLoop will be canceled automatically when the node shuts
    // down.
    connectedNode.executeCancellableLoop(new CancellableLoop() {
    	
      @Override
      protected void setup() {
      }

      @Override
      public void loop() throws InterruptedException {
    		Twist cmd = publisher.newMessage();
        if(PocketSphinxROS.send)
        {
        cmd.getLinear().setX(LX);
        cmd.getLinear().setY(LY);
        cmd.getLinear().setZ(LZ);
        cmd.getAngular().setX(AX);
        cmd.getAngular().setY(AY);
        cmd.getAngular().setZ(AZ);
        publisher.publish(cmd);
        }
       Thread.sleep(100);
      }
    });
  }
}
这一篇代码讲述控制机器人运动(电机)的消息发布。这里使用geometry_msgs/Twist格式发布到cmd_vel主题。这里消息参数分为6个,线性运动的三个轴数据,角运动的三个轴数据。默认机器人正方向为线性X轴方向,头顶向上为Z轴。官方定义:

Vector3  linear
Vector3  angular

比如前进:

			TalkParam.AX=0;
			TalkParam.AY=0;
			TalkParam.AZ=0;
			TalkParam.LX=0.4f;
			TalkParam.LY=0;
			TalkParam.LZ=0;
后退则给LX负值。

左转:(这里的左转是原地左转,因为你也看到,没有给线速度)这里AZ表示绕Z轴转动。

			TalkParam.AX=0;
			TalkParam.AY=0;
			TalkParam.AZ= 0.6f;
			TalkParam.LX=0;
			TalkParam.LY=0;
			TalkParam.LZ=0;
右转则给负值。具体速度大小相关于机器人电机参数和底层参数,所以具体机器人具体测试。

以上给出的是机器人常用到的几种消息发送格式,你也可以找到官方提供的其他消息格式,当然你也可以自己定义所发送消息的格式。


by:season




你可能感兴趣的:(Publisher,ROS,rosjava,android_core)