ROS Resources: Documentation | Support | Discussion Forum | Index | Service Status | Q&A answers.ros.org

# Compiling a Simple Plugin in ROS2

I am trying to work through the simple plugin example (http://wiki.ros.org/pluginlib/Tutoria...) but cannot get it to build for ROS2.

Trying to use https://docs.ros.org/en/foxy/Guides/A... and the details in the tutorial, but I have limited CMake experience and cannot get it to build. Are there available examples that use ROS2?

Any help would be greatly appreciated.

EDIT

Been trying to piece together a few different resources and have got things to build, but now the library can't be found so I must be doing something wrong.

The plugin failed to load for some reason. Error: %sCould not find library corresponding to plugin


I've set up two packages, once containing the base class and one containing the plugins

## Folder structure

src
-controller
-include
-Controller.h
-src
-ControlFramework.cpp
CMakeLists.txt
package.xml
-linear_controller
-include
-LinearController1.h
-LinearController2.h
-src
-LinearController1.cpp
-LinearController2.cpp
CMakeLists.txt
linear_controller_plugins.xml
package.xml


# Base Class

## Controller.h

#pragma once

namespace control_base
{
class Controller
{
public:
Controller() {};
virtual ~Controller() {};

virtual bool initialize(double p, double i, double d) = 0;
virtual double computeFeedback(double error) = 0;
};
}


## ControlFramework.cpp

#include <iostream>
#include <controller/Controller.h>

using namespace std;

int main(int argc, char** argv)
{

try
{
triangle->initialize(10.0, 0.0, 0.0);

square->initialize(5.0, 0.0, 0.0);

cout << "Triangle area: %.2f" << triangle->computeFeedback(2.0);
cout << "Square area: %.2f" << square->computeFeedback(2.0);
}
catch(pluginlib::PluginlibException& ex)
{
cout << "The plugin failed to load for some reason. Error: %s" << ex.what();
}

return 0;
}


## CMakeLists.txt

cmake_minimum_required(VERSION 3.5)
project(controller)

# Default to C++14
if(NOT CMAKE_CXX_STANDARD)
set(CMAKE_CXX_STANDARD 14)
endif()

if(CMAKE_COMPILER_IS_GNUCXX OR CMAKE_CXX_COMPILER_ID MATCHES "Clang")
endif()

# find dependencies
find_package(ament_cmake REQUIRED)
find_package(pluginlib REQUIRED)

#Include directories
include_directories(
include
)

set(plugins_dependencies
pluginlib
)

add_executable(${PROJECT_NAME} src/ControlFramework.cpp ) ament_target_dependencies(${PROJECT_NAME} ${plugins_dependencies}) install(TARGETS${PROJECT_NAME}
DESTINATION lib/${PROJECT_NAME} ) install(DIRECTORY include/ DESTINATION include/ ) ament_package()  ## package.xml <?xml version="1.0"?> <?xml-model href="http://download.ros.org/schema/package_format3.xsd" schematypens="http://www.w3.org/2001/XMLSchema"?> <package format="3"> <name>controller</name> <version>0.0.0</version> <description>TODO: Package description</description> <maintainer email="angus@todo.todo">angus</maintainer> <license>TODO: License declaration</license> <buildtool_depend>ament_cmake</buildtool_depend> <depend>pluginlib</depend> <test_depend>ament_lint_auto</test_depend> <test_depend>ament_lint_common</test_depend> <export> <build_type>ament_cmake</build_type> </export> </package>  # Plugin Package ## LinearController1.h #pragma once #include <pluginlib/class_list_macros.hpp> #include <controller/Controller.h> // Inheriting the base class namespace control_plugins { class LinearController1 : public control_base::Controller { public: LinearController1() {}; // Constructor // No destructor! bool initialize(double p, double i, double d); double computeFeedback(double error); private: double _p_gain{0}; double _i_gain{0}; double _d_gain{0}; }; }  ## LinearController1.cpp #include <linear_controller/LinearController1.h> namespace control_plugins { bool LinearController1::initialize(double p, double i, double d) { _p_gain = p; _i_gain = i; _d_gain = d; return true; } double LinearController1::computeFeedback(double ... edit retag close merge delete ## 2 Answers Sort by » oldest newest most voted So Using the diff_drive_controller I made quite a few changes to get things working: Created Separate packages for plugins, base and executable: linear_controller (Contains Plugins) controller (Contains Base Class) control_framework (Contains Executable) I then got the controller CMake to look very similar tot he controller_interface CMake and treated it as an exported library One error I had in the code that I think was actually a large part of the problem was: pluginlib::ClassLoader<control_base::Controller> ctrl_loader("linear_controller", "control_base::Controller");  Changed to name the right package containing the base class: pluginlib::ClassLoader<control_base::Controller> ctrl_loader("controller", "control_base::Controller");  Thanks for the help and pointing me in the right direction! more Using the diff_drive_controller as an example, from what I can see these are potential fixes: • You want to specify a SHARED library for your plugins (this is not the default anymore in ROS 2 like it is in ROS 1 when you make a library). You can do this by changing add_library(${PROJECT_NAME} src/LinearController1.cpp src/LinearController1.cpp )

to

• The xml where you specify the plugins, the library path shouldn't be "/liblinear_controller". instead it should probably just be "linear_controller".

• The pluginlib_export_plugin_description_file(linear_controller linear_controller_plugins.xml) line in the CMakeLists.txt for your plugin package I believe should be pluginlib_export_plugin_description_file(controller linear_controller_plugins.xml)

more

Thanks very much for the info and direction. I think your fixes were definitely necessary but still getting the same error.

Interestingly enough I still need to manually include the control/Controller.h file for it to build, so I think I am doing something wrong in the package containing my base class! So working through the controller_interface example as well. Will post when I get things working.

( 2021-06-14 17:11:02 -0500 )edit