机器人工程专业实践镜像2021版-功能扩展-coppeliasim+webots

Posted zhangrelay

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了机器人工程专业实践镜像2021版-功能扩展-coppeliasim+webots相关的知识,希望对你有一定的参考价值。

镜像虽然提供了大部分课程所需功能,但同样支持扩展。这里以两款仿真软件为例

  • coppeliasim
  • webots

其实就是在官网下载,解压到硬盘就可以使用的。

分别解压就行。

启动V-Rep(新版为coppeliasim) :

  • ./vrep.sh

启动webots:

  • ./webots

 等待启动完成,即可愉快玩耍。忽略更新。

 

缺少的功能包依据上学期课程讲解,或者依据提示补充安装即可。

现在打开一个cpp案例:

尝试一下编译:

完全可以正常使用。

 

void Driver::displayHelp() {
  string s("Commands:\\n"
           " 这只是一个测试^_^\\n"
           " I for displaying the commands\\n"
           " A for avoid obstacles\\n"
           " F for move forward\\n"
           " S for stop\\n"
           " T for turn\\n"
           " R for positioning ROBOT1 at (0.1,0.3)\\n"
           " G for knowing the (x,z) position of ROBOT1");
  cout << s << endl;
}

 

 

webots中C++的案例都可以直接编译后使用,非常方便。

更多案例自主学习即可。

// Copyright 1996-2020 Cyberbotics Ltd.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

/*
 * Description:  This controller gives to its node the following behavior:
 *               Listen the keyboard. According to the pressed key, send a
 *               message through an emitter or handle the position of Robot1
 */

#include <webots/Emitter.hpp>
#include <webots/Field.hpp>
#include <webots/Keyboard.hpp>
#include <webots/Node.hpp>
#include <webots/Supervisor.hpp>

#include <stdlib.h>
#include <cstring>
#include <iostream>
#include <string>

using namespace std;
using namespace webots;

class Driver : public Supervisor {
public:
  Driver();
  void run();

private:
  static void displayHelp();
  int timeStep;
  Emitter *emitter;
  Field *translationField;
  Keyboard *keyboard;
  double x;
  double z;
  double translation[3];
};

Driver::Driver() {
  timeStep = 128;
  x = 0.1f;
  z = 0.3f;
  translation[0] = x;
  translation[1] = 0;
  translation[2] = z;
  emitter = getEmitter("emitter");
  Node *robot = getFromDef("ROBOT1");
  if (!robot)
    // robot might be NULL if the controller is about to quit
    exit(1);

  translationField = robot->getField("translation");
  keyboard = getKeyboard();
  keyboard->enable(timeStep);
}

void Driver::run() {
  string previous_message("");
  string message("");

  displayHelp();

  // main loop
  while (step(timeStep) != -1) {
    // Read sensors; update message according to the pressed keyboard key
    int k = keyboard->getKey();
    switch (k) {
      case 'A':
        message.assign("avoid obstacles");
        break;
      case 'F':
        message.assign("move forward");
        break;
      case 'S':
        message.assign("stop");
        break;
      case 'T':
        message.assign("turn");
        break;
      case 'I':
        displayHelp();
        break;
      case 'G': {
        const double *translationValues = translationField->getSFVec3f();
        cout << "ROBOT1 is located at (" << translationValues[0] << "," << translationValues[2] << ")" << endl;
        break;
      }
      case 'R':
        cout << "Teleport ROBOT1 at (" << x << "," << z << ")" << endl;
        translationField->setSFVec3f(translation);
        break;
      default:
        message.clear();
    }

    // send actuators commands; send a new message through the emitter device
    if (!message.empty() && message.compare(previous_message)) {
      previous_message.assign(message);
      cout << "Please, " << message.c_str() << endl;
      emitter->send(message.c_str(), (int)strlen(message.c_str()) + 1);
    }
  }
}

void Driver::displayHelp() {
  string s("Commands:\\n"
           " 这只是一个测试^_^\\n"
           " I for displaying the commands\\n"
           " A for avoid obstacles\\n"
           " F for move forward\\n"
           " S for stop\\n"
           " T for turn\\n"
           " R for positioning ROBOT1 at (0.1,0.3)\\n"
           " G for knowing the (x,z) position of ROBOT1");
  cout << s << endl;
}

int main() {
  Driver *controller = new Driver();
  controller->run();
  delete controller;
  return 0;
}
// Copyright 1996-2020 Cyberbotics Ltd.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

/*
 * Description:  This controller gives to its robot the following behavior:
 *               According to the messages it receives, the robot change its
 *               behavior.
 */

#include <webots/Camera.hpp>
#include <webots/DistanceSensor.hpp>
#include <webots/Motor.hpp>
#include <webots/Receiver.hpp>
#include <webots/Robot.hpp>
#include <webots/utils/AnsiCodes.hpp>

#include <algorithm>
#include <iostream>
#include <limits>
#include <string>

using namespace std;
using namespace webots;

static const double maxSpeed = 10.0;

class Slave : public Robot {
public:
  Slave();
  void run();

private:
  enum Mode { STOP, MOVE_FORWARD, AVOID_OBSTACLES, TURN };

  static double boundSpeed(double speed);

  int timeStep;
  Mode mode;
  Receiver *receiver;
  Camera *camera;
  DistanceSensor *distanceSensors[2];
  Motor *motors[2];
};

Slave::Slave() {
  timeStep = 32;
  mode = AVOID_OBSTACLES;
  camera = getCamera("camera");
  camera->enable(4 * timeStep);
  receiver = getReceiver("receiver");
  receiver->enable(timeStep);
  motors[0] = getMotor("left wheel motor");
  motors[1] = getMotor("right wheel motor");
  motors[0]->setPosition(std::numeric_limits<double>::infinity());
  motors[1]->setPosition(std::numeric_limits<double>::infinity());
  motors[0]->setVelocity(0.0);
  motors[1]->setVelocity(0.0);
  string distanceSensorNames("ds0");
  for (int i = 0; i < 2; i++) {
    distanceSensors[i] = getDistanceSensor(distanceSensorNames);
    distanceSensors[i]->enable(timeStep);
    distanceSensorNames[2]++;  // for getting "ds1","ds2",...
  }
}

double Slave::boundSpeed(double speed) {
  return std::min(maxSpeed, std::max(-maxSpeed, speed));
}

void Slave::run() {
  // main loop
  while (step(timeStep) != -1) {
    // Read sensors, particularly the order of the supervisor
    if (receiver->getQueueLength() > 0) {
      string message((const char *)receiver->getData());
      receiver->nextPacket();

      cout << "I should " << AnsiCodes::RED_FOREGROUND << message << AnsiCodes::RESET << "!" << endl;

      if (message.compare("avoid obstacles") == 0)
        mode = AVOID_OBSTACLES;
      else if (message.compare("move forward") == 0)
        mode = MOVE_FORWARD;
      else if (message.compare("stop") == 0)
        mode = STOP;
      else if (message.compare("turn") == 0)
        mode = TURN;
    }
    double delta = distanceSensors[0]->getValue() - distanceSensors[1]->getValue();
    double speeds[2] = {0.0, 0.0};

    // send actuators commands according to the mode
    switch (mode) {
      case AVOID_OBSTACLES:
        speeds[0] = boundSpeed(maxSpeed / 2.0 + 0.1 * delta);
        speeds[1] = boundSpeed(maxSpeed / 2.0 - 0.1 * delta);
        break;
      case MOVE_FORWARD:
        speeds[0] = maxSpeed;
        speeds[1] = maxSpeed;
        break;
      case TURN:
        speeds[0] = maxSpeed / 2.0;
        speeds[1] = -maxSpeed / 2.0;
        break;
      default:
        break;
    }
    motors[0]->setVelocity(speeds[0]);
    motors[1]->setVelocity(speeds[1]);
  }
}

int main() {
  Slave *controller = new Slave();
  controller->run();
  delete controller;
  return 0;
}

-End-


 

以上是关于机器人工程专业实践镜像2021版-功能扩展-coppeliasim+webots的主要内容,如果未能解决你的问题,请参考以下文章

机器人工程专业实践镜像2021版-含现代控制理论机器人控制器ROS2ESP32Webots和导航实践(tianbot_mini)

机器人工程专业实践镜像2021版-含现代控制理论机器人控制器ROS2ESP32Webots和导航实践(tianbot_mini)

机器人工程专业相关课程实践镜像2021测试版(ROS2+Nav2+ESP32+51+……)

机器人工程专业相关课程实践镜像2021测试版(ROS2+Nav2+ESP32+51+……)

HML_FwLib系列在镜像中的使用说明

HML_FwLib系列在镜像中的使用说明