lb8820265 发表于 2022-11-1 16:04

41“万里”树莓派小车——ROS学习(ROSBridge控制小乌龟)

<div class='showpostmsg'> 本帖最后由 lb8820265 于 2022-11-3 22:29 编辑

<p>&nbsp; &nbsp; &nbsp;前面介绍了<a href="https://bbs.eeworld.com.cn/thread-1200059-1-1.html" target="_blank">使用键盘控制小乌龟</a>,<a href="https://bbs.eeworld.com.cn/thread-1205068-1-1.html" target="_blank">使用指令控制小乌龟</a>,使用自己编写的<a href="https://bbs.eeworld.com.cn/thread-1223275-1-1.html" target="_blank">C语言控制小乌龟</a>,这里介绍使用网络控制小乌龟,也即可以通过电脑或者手机操控小乌龟。前面有介绍过<a href="https://bbs.eeworld.com.cn/thread-1187305-1-1.html" target="_blank">Linux与PC和Android进行通信的TCP和UDP方法</a>,但是在ROS下有了新的方法,那就是<a href="http://wiki.ros.org/rosbridge_suite" target="_blank">ROSBridge</a>,<a href="https://github.com/RobotWebTools/rosbridge_suite" target="_blank">官方GitHub库</a>。</p>

<p>&nbsp; &nbsp; &nbsp;ROSBridge是一个可用于非ROS系统和ROS系统进行通信的功能包,非ROS的系统使用指定数据内容的基于JSON(或BSON)格式的网络请求(ROSBridge支持TCP、UDP、WebSocket三种网络通讯方式)来调用ROS的功能。</p>

<p><span style="font-size:18px;"><strong>操作步骤</strong></span></p>

<p><strong>1. ROS安装rosbridge组件</strong></p>

<pre>
<code>sudo apt-get install ros-noetic-rosbridge-server</code></pre>

<p><strong>2. 编写网页代码</strong></p>

<p>将以下代码复制到文本文件中,并命名为&ldquo;turtlewebcontrol.html&rdquo;,源码文件见帖子最后。</p>

<pre>
<code class="language-html">&lt;!DOCTYPE html&gt;
&lt;html&gt;
&lt;head&gt;
&lt;meta charset="utf-8" /&gt;
&lt;script type="text/javascript" src="http://static.robotwebtools.org/EventEmitter2/current/eventemitter2.min.js"&gt;&lt;/script&gt;
&lt;script type="text/javascript" src="http://static.robotwebtools.org/roslibjs/current/roslib.min.js"&gt;&lt;/script&gt;
&lt;style type="text/css"&gt;
    #box1{
        width: 44px;
        height:44px;
        position: absolute;
        background: lightskyblue;
    }
&lt;/style&gt;
&lt;script type="text/javascript" type="text/javascript"&gt;
  // Connecting to ROS
  var ros = new ROSLIB.Ros({
   url : 'ws://localhost:9090'
// url : 'ws://192.168.31.159:9090'
  });
  var isconected=false;
  //判断是否连接成功并输出相应的提示消息到web控制台
  ros.on('connection', function() {
    isconected=true;
    console.log('Connected to websocket server.');
    subscribe();
  });
  ros.on('error', function(error) {
    isconected=false;
    console.log('Error connecting to websocket server: ', error);
  });
  ros.on('close', function() {
    isconected=false;
    console.log('Connection to websocket server closed.');
    unsubscribe();
  });
  // Publishing a Topic
  var cmdVel = new ROSLIB.Topic({
    ros : ros,
    name : 'turtle1/cmd_vel',
    messageType : 'geometry_msgs/Twist'
  });//创建一个topic,它的名字是'/cmd_vel',,消息类型是'geometry_msgs/Twist'
  var twist = new ROSLIB.Message({
    linear : {
      x : 0.0,
      y : 0.0,
      z : 0.0
    },
    angular : {
      x : 0.0,
      y : 0.0,
      z : 0.0
    }
  });//创建一个message
  function control_move(direction){
    twist.linear.x = 0.0;
    twist.linear.y = 0;
    twist.linear.z = 0;
    twist.angular.x = 0;
    twist.angular.y = 0;
    twist.angular.z = 0.0;
    switch(direction){
      case 'up':
        twist.linear.x = 2.0;
        break;
      case 'down':
        twist.linear.x = -2.0;
      break;
      case 'left':
        twist.angular.z = 2.0;
      break;
      case 'right':
        twist.angular.z = -2.0;
      break;
    }
    cmdVel.publish(twist);//发布twist消息
  }
  var timer=null;    
  function buttonmove(){    
    var oUp=document.getElementById('up');
    var oDown=document.getElementById('down');
    var oLeft=document.getElementById('left');
    var oRight=document.getElementById('right'); 
    oUp.onmousedown=function ()
    {
        Move('up');        
    }
    oDown.onmousedown=function ()
    {
        Move('down');        
    }
    oLeft.onmousedown=function ()
    {
        Move('left');        
    }
    oRight.onmousedown=function ()
    {
        Move('right');       
    }
    oUp.onmouseup=oDown.onmouseup=oLeft.onmouseup=oRight.onmouseup=function ()
    {
        MouseUp ();
    }      
  }

  function keymove (event) {    
    event = event || window.event;/*||为或语句,当IE不能识别event时候,就执行window.event 赋值*/
    console.log(event.keyCode);
    switch (event.keyCode){/*keyCode:字母和数字键的键码值*/          
        /*65,87,68,83分别对应awds*/
        case 65:                 
            Move('left');
            break;
        case 87:              
            Move('up');
            break;
        case 68:              
            Move('right');
            break;
        case 83:
            Move('down');
            break;
        default:
            break;
    }
  }
  var MoveTime=20;
  function Move (f){
    clearInterval(timer);
    timer=setInterval(function (){          
     control_move(f)      
    },MoveTime);
  }        
  function MouseUp ()
  {
      clearInterval(timer);        
  }
  function KeyUp(event){
      MouseUp();
  }
  window.onload=function ()
  {  
        buttonmove();                
        document.onkeyup=KeyUp;
        document.onkeydown=keymove;           
        Movebox();    
  }
  // Subscribing to a Topic
  var listener = new ROSLIB.Topic({
    ros : ros,
    name : '/turtle1/pose',
    messageType : 'turtlesim/Pose'
  });//创建一个topic,它的名字是'/turtle1/pose',,消息类型是'turtlesim/Pose',用于接收乌龟位置信息
  var turtle_x=0.0;
  var turtle_y=0.0;

  function subscribe()//在连接成功后,控制div的位置,
  {
     listener.subscribe(function(message) {         
       turtle_x=message.x;
       turtle_y=message.y;
       document.getElementById("output").innerHTML = ('Received message on ' + listener.name +'  x: ' + message.x+" ,y: "+message.y);
     });
  }

  function unsubscribe()//在断开连接后,取消订阅
  {
     listener.unsubscribe();    
  }

  function Movebox ()
  {    
    var obox=document.getElementById("box1");    
    var timer=null;
    clearInterval(timer);
    timer=setInterval(function (){
      if(!isconected)
      {
        obox.style.left = '0px';
        obox.style.top = '0px';        
      } else {
        obox.style.left =Math.round(60*turtle_x)-330+"px";
        console.log(obox.style.left)
        obox.style.top =330-Math.round(60*turtle_y)+"px";
        console.log(obox.style.top)
      }
    },20);
 }
&lt;/script&gt;
&lt;/head&gt;
&lt;body&gt;
  &lt;h1&gt;rosbridge Simple example--Move turtle with teleop or button &lt;/h1&gt;
  &lt;p&gt;First,on robot machine,run: roslaunch rosbridge_server rosbridge_websocket.launch&lt;/p&gt;
  &lt;p&gt;second,on robot machine,run: rosrun turtlesim turtlesim_node&lt;/p&gt;
  &lt;p&gt;third,on this webpage control turtle with up,down,left,right key&lt;/p&gt;
  &lt;p&gt;Check your Web Console for output.&lt;/p&gt;
  &lt;input type="button" value="前行" id="up"&gt;
  &lt;input type="button" value="后退" id="down"&gt;
  &lt;input type="button" value="左转" id="left"&gt;
  &lt;input type="button" value="右转" id="right"&gt;
  &lt;p&gt;@author Joshua   2021-04-23&lt;/p&gt;
  &lt;p id = "output"&gt;&lt;/p&gt;
  &lt;div id="mbox" style="width:704px;height:704px;border:1px solid red;position: relative;"&gt;
    &lt;div id="box1" style="margin-left:330px;margin-top:330px;position:absolute;" &gt;&lt;/div&gt;    
  &lt;/div&gt;
&lt;/body&gt;
&lt;/html&gt;</code></pre>

<p><span style="font-size:18px;"><b>演示操作</b></span></p>

<p><strong><span style="font-size:16px;">1. 启动内核</span></strong></p>

<pre>
<code>roscore</code></pre>

<p><strong>2. 启动小乌龟</strong></p>

<pre>
<code>rosrun turtlesim turtlesim_node</code></pre>

<p><strong>3. 开启rosbridgea服务</strong></p>

<pre>
<code>roslaunch rosbridge_server rosbridge_websocket.launch</code></pre>

<p><strong>4. 用浏览器打开网页,在网页中点击按钮就可以控制小乌龟</strong></p>

<p>&nbsp; &nbsp; &nbsp; 上面是使用树莓派的网页控制小乌龟,同样也可以使用其他局域网内的电脑控制树莓派上的小乌龟,</p>

<p>&nbsp; &nbsp; &nbsp; 将网页源代码中的如下位置中的地址改为树莓派的IP地址即可(9090是默认端口)。</p>

<p> &nbsp;&nbsp; &nbsp; &nbsp;使用Windows电脑与树莓派在同一个局域网,打开网页同样能够控制小乌龟。</p>

<p><strong><span style="font-size:18px;">参考</span></strong></p>

<p>&nbsp; &nbsp;&nbsp;<a href="https://blog.csdn.net/dzjoke/article/details/116056180"><u>初识Rosbridge--利用rosbridge实现网页控制小乌龟移动</u></a></p>

<p><span style="font-size:18px;"><strong>问题</strong></span></p>

<p>&nbsp; &nbsp;如何使用手机控制小乌龟呢?</p>

<p><span style="font-size:18px;"><strong>源代码</strong></span></p>

<p>&nbsp; &nbsp;GitHub:<a href="https://github.com/wanli-car/Examples/tree/master/Others" target="_blank">https://github.com/wanli-car/Examples/tree/master/Others</a></p>

<p>&nbsp; &nbsp;Gitee:<a href="https://gitee.com/wanli-car/Examples/tree/master/Others" target="_blank">https://gitee.com/wanli-car/Examples/tree/master/Others</a></p>
</div><script>                                var loginstr = '<div class="locked">查看精华帖全部内容,请<a href="javascript:;"   style="color:#e60000" class="loginf">登录</a>或者<a href="https://bbs.eeworld.com.cn/member.php?mod=register_eeworld.php&action=wechat" style="color:#e60000" target="_blank">注册</a></div>';
                               
                                if(parseInt(discuz_uid)==0){
                                                                                        (function($){
                                                        var postHeight = getTextHeight(400);
                                                        $(".showpostmsg").html($(".showpostmsg").html());
                                                        $(".showpostmsg").after(loginstr);
                                                        $(".showpostmsg").css({height:postHeight,overflow:"hidden"});
                                                })(jQuery);
                                }
</script><script type="text/javascript">(function(d,c){var a=d.createElement("script"),m=d.getElementsByTagName("script"),eewurl="//counter.eeworld.com.cn/pv/count/";a.src=eewurl+c;m.parentNode.insertBefore(a,m)})(document,523)</script>

lugl4313820 发表于 2022-11-5 07:37

<p>&nbsp;ROSBridge是一个可用于非ROS系统和ROS系统进行通信的功能包,非ROS的系统使用指定数据内容的基于JSON(或BSON)格式的网络请求(ROSBridge支持TCP、UDP、WebSocket三种网络通讯方式)来调用ROS的功能。</p>

<p>慢慢学习大佬的作品。</p>

leilei0000 发表于 2023-2-22 15:37

<p>&nbsp;ROSBridge是一个可用于非ROS系统和ROS系统进行通信的功能包,非ROS的系统使用指定数据内容的基于JSON(或BSON)格式的网络请求(ROSBridge支持TCP、UDP、WebSocket三种网络通讯方式)来调用ROS的功能。</p>

<p>慢慢学习大佬的作品。</p>

lkh747566933 发表于 2023-11-25 01:54

买了一个树莓派4B 2G版的,可惜忙的要死,买回来就接灰了。而且后面还降价了一多半
页: [1]
查看完整版本: 41“万里”树莓派小车——ROS学习(ROSBridge控制小乌龟)