ros机器人编程实践(15.2)- 使用科大讯飞语音控制turtlebot导航

183
0
2020年9月9日 12时19分

一、前言

接上一篇博客:ros机器人编程实践(15.1)- 使用科大讯飞语音控制turtlebot导航

二、使用科大讯飞语音SDK

ros机器人编程实践(15.2)- 使用科大讯飞语音控制turtlebot导航插图

 

对着上一篇博客中科大讯飞的安装教程,创建了robot_voice的基于roscpp的包创建robot_voice包教程。科大讯飞sdk的安装教程那位博主写了四篇博客介绍已经很详细,就不累述了。

 

2.1 测试语音识别

 

//启动ros服务
roscore
//启动语音识别节点
rosrun robot_voice iat_publish
//发布唤醒语音识别的话题消息,任意消息即可唤醒
rostopic pub /voiceWakeup  std_msgs/String  "data: 'anny string'"

 

效果如下:

 

ros机器人编程实践(15.2)- 使用科大讯飞语音控制turtlebot导航插图(1)

 

当然还可以在iat_publish发布的消息中查看语音识别的效果:

 

rostopic echo /voiceWords

 

ros机器人编程实践(15.2)- 使用科大讯飞语音控制turtlebot导航插图(2)

 

这个识别是需要联网的。

2.1 测试语音合成

详细教程在这:语音合成,博主写的很详细了,这里也不累述。

 

rosrun xfei_asr tts_subscribe_speak
rostopic pub xfwords std_msgs/String "你好,世界!"

 

ros机器人编程实践(15.2)- 使用科大讯飞语音控制turtlebot导航插图(3)

 

ros机器人编程实践(15.2)- 使用科大讯飞语音控制turtlebot导航插图(4)

 

语音播报效果极佳!!!

三、代码实现

3.1 修改语音识别的源码

首先修改语音识别的源码,他需要识别一次唤醒一次,我们希望它一直监听。

 

sudo gedit ~/wanderbot_ws/src/robot_voice/src/iat_publish.cpp

 

看下源码发现他是在收到/voiceWakeup话题的任何消息后进入回调函数实现唤醒语音识别,如下图中代码:

 

ros机器人编程实践(15.2)- 使用科大讯飞语音控制turtlebot导航插图(5)

ros机器人编程实践(15.2)- 使用科大讯飞语音控制turtlebot导航插图(6)

 

那好办,把唤醒函数抄一份,我们不通过回调来调用,我们主动的调用它。

 

如下图修改:

void WakeUp(const std_msgs::String::ConstPtr& msg)
{
    printf("waking up\r\n");
    usleep(700*1000);
    wakeupFlag=1;
}
void Wake()
{
    printf("waking up\r\n");
    usleep(700*1000);
    wakeupFlag=1;
}

 

ros机器人编程实践(15.2)- 使用科大讯飞语音控制turtlebot导航插图(7)

 

然后在每次识别完成发布了识别消息后唤醒识别系统。

 

如下图倒数第五行,调用了我们自己写的唤醒函数:

 

ros机器人编程实践(15.2)- 使用科大讯飞语音控制turtlebot导航插图(8)

 

ros里写cpp的脚本是需要编译的,所以回到工作区编译:

 

cd ~/wanderbot_ws
catkin_make
source ./devel/setup.bash

 

这里非常重要哦,之前写的都是Python的脚本是不需要这一笔操作的,和容易忘记了,忘了的话你每次修改cpp文件都会发现没有效果。

 

然后测试下我们改写的效果:

 

//启动ros服务
roscore
//启动语音识别节点
rosrun robot_voice iat_publish

 

ros机器人编程实践(15.2)- 使用科大讯飞语音控制turtlebot导航插图(9)

 

这时候运行脚本就自动唤醒了,而且一直在监听。

3.2 创建语音识别结果的监听脚本

cd ~/wanderbot_ws/src/wanderbot/src
sudo gedit voice_contrl.py

 

如果看了我《ros机器人编程实践(8.9.10)-用turtlebot3仿真实现机器人在多点间来回导航》这篇博客应该知道这个脚本是在turtlebot多点导航的基础上修改的。

 

#!/usr/bin/env python
# -*- coding: UTF-8 -*-
import rospy
import actionlib
import roslib;
import rospy
from std_msgs.msg import String#添加了接受的消息类型
 
from move_base_msgs.msg import MoveBaseAction, MoveBaseGoal

 
waypoints = [  #导航的坐标点
    [(1.522, 0.444, 0.0), (0.0, 0.0, -0.519, 0.85)],
    [(-2.0432, -0.439, 0.0), (0.0, 0.0, -0.559, 0.82902)]
]
 
 
def goal_pose(pose):  #坐标点转换成对应的消息类型
    goal_pose = MoveBaseGoal()
    goal_pose.target_pose.header.frame_id = 'map'
    goal_pose.target_pose.pose.position.x = pose[0][0]
    goal_pose.target_pose.pose.position.y = pose[0][1]
    goal_pose.target_pose.pose.position.z = pose[0][2]
    goal_pose.target_pose.pose.orientation.x = pose[1][0]
    goal_pose.target_pose.pose.orientation.y = pose[1][1]
    goal_pose.target_pose.pose.orientation.z = pose[1][2]
    goal_pose.target_pose.pose.orientation.w = pose[1][3]
 
    return goal_pose

def callback(msg):
	print msg.data#这里注意需要.data而不是msg本身,data里存的才是字符串
	if msg.data.find('one') > -1:
            pose = waypoints[0]
        elif msg.data.find('three') > -1:
            pose = waypoints[1]
        else:
            return;

        client = actionlib.SimpleActionClient('move_base', MoveBaseAction)  # <3>
        client.wait_for_server()
            
        print("goal:x=%f y=%f"%(pose[0][0],pose[0][1]))
        goal = goal_pose(pose)
        client.send_goal(goal)
        client.wait_for_result()


 
 
if __name__ == '__main__':

    rospy.init_node('message_publisher')

    pub=rospy.Publisher('voiceWakeup',String,queue_size = 1)

    rospy.sleep(1)
    pub.publish('wake up')#唤醒语音识别系统

    sub = rospy.Subscriber('voiceWords', String,callback)#监听识别结果的消息传入回调函数
    rospy.spin()

 

好了到这里就大功告成了。

四、效果测试

启动仿真环境:

roslaunch turtlebot3_gazebo turtlebot3_world.launch

 

启动rviz:

roslaunch turtlebot3_navigation turtlebot3_navigation.launch map_file:=$HOME/map.yaml

 

启动语音检测脚本:

rosrun robot_voice iat_publish

 

启动语音控制导航脚本:

rosrun wanderbot voice_contrl.py 

 

ros机器人编程实践(15.2)- 使用科大讯飞语音控制turtlebot导航插图(10)

ros机器人编程实践(15.2)- 使用科大讯飞语音控制turtlebot导航插图(11)

 

 

 

 

 

 

 

 

~自己玩玩吧

 

Tips:识别关键字是‘one’ 和‘three’

 

为什么不用two呢。。。。因为他会识别成‘to’。。。我是醉了

发表评论

后才能评论