YARP
Yet Another Robot Platform
 
Loading...
Searching...
No Matches
Add a plugin to YARP
+ Collaboration diagram for Add a plugin to YARP:

Making a single plugin

Let's take the FakeFrameGrabber example device developed in Getting Started with YARP Devices and turn it into a plugin. Make a directory called fake_grabber (or whatever you like), and add the following as fake_grabber/FakeFrameGrabber.h.

/*
* SPDX-FileCopyrightText: 2006-2021 Istituto Italiano di Tecnologia (IIT)
* SPDX-FileCopyrightText: 2006-2010 RobotCub Consortium
* SPDX-License-Identifier: BSD-3-Clause
*/
#include <yarp/os/all.h>
#include <yarp/dev/all.h>
private:
int w, h;
public:
h = w = 0;
}
bool open(int w, int h) {
this->w = w;
this->h = h;
return w>0 && h>0;
}
virtual bool open(yarp::os::Searchable& config) {
// extract width and height configuration, if present
// otherwise use 128x128
int desiredWidth = config.check("w",yarp::os::Value(128)).asInt32();
int desiredHeight = config.check("h",yarp::os::Value(128)).asInt32();
return open(desiredWidth,desiredHeight);
}
virtual bool close() {
return true; // easy
}
virtual int height() const {
return h;
}
virtual int width() const {
return w;
}
};
fakeFrameGrabber: A fake camera for testing.
int width() const override
Return the width of each frame.
int height() const override
Return the height of each frame.
FakeFrameGrabber()=default
bool open(yarp::os::Searchable &config) override
yarp::dev::ReturnValue getImage(yarp::sig::ImageOf< yarp::sig::PixelRgb > &image) override
Get an image from the frame grabber.
bool close() override
Close the DeviceDriver.
Interface implemented by all device drivers.
A base class for nested structures that can be searched.
Definition Searchable.h:31
virtual bool check(const std::string &key) const =0
Check if there exists a property of the given name.
A single value (typically within a Bottle).
Definition Value.h:44
Typed image class.
Definition Image.h:603

And add this as fake_grabber/FakeFrameGrabber.cpp:

/*
* SPDX-FileCopyrightText: 2006-2021 Istituto Italiano di Tecnologia (IIT)
* SPDX-FileCopyrightText: 2006-2010 RobotCub Consortium
* SPDX-License-Identifier: BSD-3-Clause
*/
#include <yarp/os/all.h>
#include <yarp/dev/all.h>
private:
int w, h;
public:
h = w = 0;
}
bool open(int w, int h) {
this->w = w;
this->h = h;
return w>0 && h>0;
}
virtual bool open(yarp::os::Searchable& config) {
// extract width and height configuration, if present
// otherwise use 128x128
int desiredWidth = config.check("w",yarp::os::Value(128)).asInt32();
int desiredHeight = config.check("h",yarp::os::Value(128)).asInt32();
return open(desiredWidth,desiredHeight);
}
virtual bool close() {
return true; // easy
}
virtual int height() const {
return h;
}
virtual int width() const {
return w;
}
};

Here's a quick test program for the device, call it fake_grabber/test_fake_grabber.cpp:

/*
* SPDX-FileCopyrightText: 2006-2021 Istituto Italiano di Tecnologia (IIT)
* SPDX-FileCopyrightText: 2006-2010 RobotCub Consortium
* SPDX-License-Identifier: BSD-3-Clause
*/
#include <stdio.h>
using namespace yarp::os;
using namespace yarp::sig;
using namespace yarp::dev;
int main(int argc, char *argv[]) {
new DriverCreatorOf<FakeFrameGrabber>("fake_grabber","grabber","FakeFrameGrabber");
Drivers::factory().add(fake_factory); // hand factory over to YARP
PolyDriver dd("fake_grabber");
if (!dd.isValid()) {
printf("fake_grabber not available\n");
return 1;
}
dd.view(grabber);
if (grabber==NULL) {
printf("*** Device failed to supply images\n");
return 1;
}
printf("*** Device can supply images\n");
if (grabber->getImage(img)) {
printf("*** Got a %dx%d image\n", img.width(), img.height());
} else {
printf("Failed to read an image\n");
return 1;
}
return 0;
}
A factory for creating driver objects of a particular type.
Definition Drivers.h:81
A base class for factories that create driver objects.
Definition Drivers.h:27
A container for a device driver.
Definition PolyDriver.h:23
A mini-server for performing network communication in the background.
size_t width() const
Gets width of image in pixels.
Definition Image.h:171
size_t height() const
Gets height of image in pixels.
Definition Image.h:177
int main(int argc, char *argv[])
Definition main.cpp:121
For streams capable of holding different kinds of content, check what they actually have.
An interface to the operating system, including Port based communication.

YARP plugins need a CMakeLists.txt that says how to build them. The CMakeLists.txt is written in the following style (this would be fake_grabber/CMakeLists.txt):

# SPDX-FileCopyrightText: 2006-2021 Istituto Italiano di Tecnologia (IIT)
# SPDX-FileCopyrightText: 2006-2010 RobotCub Consortium
# SPDX-License-Identifier: BSD-3-Clause
cmake_minimum_required(VERSION 3.19)
find_package(YARP COMPONENTS os dev REQUIRED)
# Declare a device called "fake_grabber", with C++ type
# "FakeFrameGrabber" defined in FakeFrameGrabber.h. This code sets
# up a CMake option for selecting the device, and prepares
# some initialization boilerplate code if needed.
# If the device is not selected, "SKIP_foo" will be defined.
yarp_prepare_plugin(fake_grabber
CATEGORY device
INCLUDE FakeFrameGrabber.h
EXTRA_CONFIG WRAPPER=frameGrabber_nws_yarp
)
if(NOT SKIP_fake_grabber)
yarp_add_plugin(fake_grabber)
target_sources(fake_grabber
PRIVATE
)
target_link_libraries(fake_grabber
PRIVATE
${YARP_LIBRARIES}
)
option(COMPILE_TEST "Compile fake grabber test")
if(COMPILE_TEST)
add_executable(test_fake_grabber)
target_sources(test_fake_grabber
PRIVATE
test_fake_grabber.cpp
)
target_link_libraries(test_fake_grabber PRIVATE ${YARP_LIBRARIES})
endif()
endif()
#define TYPE

This style is used so that individual plugin directories can be compiled standalone for testing purposes, but will also work when bundled into a larger library. If we configure and compile this directory, we get a test program that we can run straight away. If it works, then we could immediately plug this device into YARP.

Making a plugin library

Here we put together a library of YARP plugins from scratch.

First, let's start with a stub test program, userlib/test_userlib.cpp:

#include <stdio.h>
int main(int argc, char *argv[]) {
printf("Test program stub\n");
return 0;
}

Here's a CMakeLists.txt (userlib/CMakeLists.txt) to compile this:

cmake_minimum_required(VERSION 3.16)
find_package(YARP COMPONENTS os REQUIRED)
add_executable(test_userlib)
target_sources(test_userlib PRIVATE test_userlib.cpp)
target_link_libraries(test_userlib PRIVATE YARP::YARP_os
                                           YARP::YARP_init)

Now, let's prepare a plugin library. We need to include YarpPlugin in order to get some helper functions for this. We'll just have one plugin for now, the fake_grabber device. Here's the modified userlib/CMakeLists.txt file:

# SPDX-FileCopyrightText: 2006-2021 Istituto Italiano di Tecnologia (IIT)
# SPDX-FileCopyrightText: 2006-2010 RobotCub Consortium
# SPDX-License-Identifier: BSD-3-Clause
cmake_minimum_required(VERSION 3.19)
find_package(YARP COMPONENTS os dev REQUIRED)
yarp_begin_plugin_library(userlib)
add_subdirectory(fake_grabber)
yarp_end_plugin_library(userlib)
add_executable(test_userlib)
target_sources(test_userlib PRIVATE test_userlib.cpp)
target_link_libraries(test_userlib PRIVATE ${YARP_LIBRARIES})
target_link_libraries(test_userlib PRIVATE userlib)

This assumes that we have moved fake_grabber into the userlib directory.

Now, let's update our test program, userlib/test_userlib.cpp:

/*
* SPDX-FileCopyrightText: 2006-2021 Istituto Italiano di Tecnologia (IIT)
* SPDX-FileCopyrightText: 2006-2010 RobotCub Consortium
* SPDX-License-Identifier: BSD-3-Clause
*/
#include <stdio.h>
#include <yarp/os/all.h>
#include <yarp/dev/all.h>
using namespace yarp::os;
using namespace yarp::dev;
int main(int argc, char *argv[]) {
PolyDriver dd("fake_grabber");
if (!dd.isValid()) {
printf("fake_grabber not available\n");
return 1;
}
printf("Was able to instantiate a fake_grabber\n");
return 0;
}
#define YARP_DECLARE_PLUGINS(name)
Definition Network.h:26
#define YARP_REGISTER_PLUGINS(name)
Definition Network.h:27
Utilities for manipulating the YARP network, including initialization and shutdown.
Definition Network.h:706
The main, catch-all namespace for YARP.
Definition dirs.h:16

We can now use cmake to configure and build, either in the userlib directory, or in the userlib/fake_grabber directory. These files are available in the YARP source package, under the directory example/plugins.

Adding a plugin into YARP

In directory ${YARP_ROOT}/src/devices/CMakeLists.txt, there is a list of device directories. We could just add another line to insert fake_grabber. There is no requirement that the fake_grabber subdirectory be in any particular location. Similarly, carriers can be added in $YARP_ROOT/src/carriers/CMakeLists.txt and portmonitors in $YARP_ROOT/src/portmonitors/CMakeLists.txt.