JeVoisBase  1.21
JeVois Smart Embedded Machine Vision Toolkit Base Modules
Share this page:
Loading...
Searching...
No Matches
RoadNavigation.C
Go to the documentation of this file.
1// ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////
2//
3// JeVois Smart Embedded Machine Vision Toolkit - Copyright (C) 2016 by Laurent Itti, the University of Southern
4// California (USC), and iLab at USC. See http://iLab.usc.edu and http://jevois.org for information about this project.
5//
6// This file is part of the JeVois Smart Embedded Machine Vision Toolkit. This program is free software; you can
7// redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software
8// Foundation, version 2. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
9// without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
10// License for more details. You should have received a copy of the GNU General Public License along with this program;
11// if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
12//
13// Contact information: Laurent Itti - 3641 Watt Way, HNB-07A - Los Angeles, CA 90089-2520 - USA.
14// Tel: +1 213 740 3527 - itti@pollux.usc.edu - http://iLab.usc.edu - http://jevois.org
15// ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////
16/*! \file */
17
18#include <jevois/Core/Module.H>
19
20#include <jevois/Debug/Log.H>
21#include <jevois/Debug/Timer.H>
24
25#include <opencv2/core/core.hpp>
26#include <opencv2/imgproc/imgproc.hpp>
27
28#include <future>
29#include <linux/videodev2.h> // for v4l2 pixel types
30
31// icon by Dave Gandy in transport at flaticon
32
33//! Parameter \relates RoadNavigation
34JEVOIS_DECLARE_PARAMETER(vpconf, float, "Minimum vanishing point confidence required to send a serial message. "
35 "Note that currently, confidence values are binary (only 0 or 1), and quite conservative "
36 "(many good detections may get a confidence of 0 if they are not very clean).",
37 0.0F, roadfinder::ParamCateg);
38
39//! Road finder demo
40/*! This algorithm detects road using a compination of edge detection and tracking, and texture analysis. The algorithm
41 is an implementation of Chang, Siagian and Itti, IROS 2012, available at
42 http://ilab.usc.edu/publications/doc/Chang_etal12iros.pdf
43
44 The algorithms combines detection and tracking of line segments at the edges of the road or on the road (e.g., lane
45 dividers), and texture analysis to distinguish the road region from its surroundings. One strength of this algorithm
46 is that it requires no training. No need to drive your robot on many roads to learn about the appearance of
47 roads. The flipside of this, of course, is that driving on roads which do not look like standard roads or trails may
48 fail.
49
50 The algorithm outputs the horizontal coordinate of the vanishing point of the road, which usually is a good
51 indication of the road heading (except in very tight bends or corners).
52
53 Demo display outputs
54 --------------------
55
56 Detected line segments are shown in black and white, while segments that have been reliably tracked over multiple
57 frames are shown in thick purple. Estimated vanishing point location and confidence is shown as a big green disk on
58 the horizon line.
59
60 Note that the demo display runs much slower than the algorithm with no video output (which should be used on
61 autonomous cars), simply because drawing all the detected line segments takes a lot of time.
62
63 Serial Messages
64 ---------------
65
66 This module can send standardized serial messages as described in \ref UserSerialStyle. One 1D message is issued on
67 every video frame for the vanishing point's horizontal location.
68
69 - Serial message type: \b 1D
70 - `id`: always \b vp (shorthand for vanishing point)
71 - `x`: standardized 2D horizontal coordinate of the vanishing point
72 - `w`: always 0.
73 - `extra`: none (empty string)
74
75 See \ref UserSerialStyle for more on standardized serial messages, and \ref coordhelpers for more info on
76 standardized coordinates.
77
78 Trying it out
79 -------------
80
81 To casually try out this module, just search the web for pictures of roads and point the JeVois camera to one of
82 them. Make sure that you align the horizon line of the algorithm (which has a number of purple and green disks)
83 roughly with the horizon line in your picture. As you move the camera left and right, the location of the large
84 green disk that marks the detected vanishing point should move left and right, and should point to the vanishing
85 point of the road in your image.
86
87 When using on a mobile robot in the real world, setting the proper horizon line is essential for good operation of
88 the algorithm. This is determined by parameter \c horizon, which should be tuned according to the height and
89 tilt angle of the JeVois camera on your vehicle.
90
91
92 @author Laurent Itti
93
94 @videomapping NONE 0 0 0 YUYV 320 240 30.0 JeVois RoadNavigation
95 @videomapping NONE 0 0 0 YUYV 176 144 120.0 JeVois RoadNavigation
96 @videomapping YUYV 320 256 30.0 YUYV 320 240 30.0 JeVois RoadNavigation
97 @videomapping YUYV 176 160 120.0 YUYV 176 144 120.0 JeVois RoadNavigation
98 @email itti\@usc.edu
99 @address University of Southern California, HNB-07A, 3641 Watt Way, Los Angeles, CA 90089-2520, USA
100 @copyright Copyright (C) 2016 by Laurent Itti, iLab and the University of Southern California
101 @mainurl http://jevois.org
102 @supporturl http://jevois.org/doc
103 @otherurl http://iLab.usc.edu
104 @license GPL v3
105 @distribution Unrestricted
106 @restrictions None
107 \ingroup modules */
108class RoadNavigation : public jevois::StdModule, jevois::Parameter<vpconf>
109{
110 public:
111 // ####################################################################################################
112 //! Constructor
113 // ####################################################################################################
114 RoadNavigation(std::string const & instance) :
115 jevois::StdModule(instance), itsProcessingTimer("Processing", 30, LOG_DEBUG)
116 {
117 itsRoadFinder = addSubComponent<RoadFinder>("roadfinder");
118 }
119
120 // ####################################################################################################
121 //! Virtual destructor for safe inheritance
122 // ####################################################################################################
123 virtual ~RoadNavigation() { }
124
125 // ####################################################################################################
126 //! Processing function, no video out
127 // ####################################################################################################
128 virtual void process(jevois::InputFrame && inframe) override
129 {
130 // Wait for next available camera image, convert it to gray, and release it:
131 cv::Mat imggray = inframe.getCvGRAY();
132
133 // Compute the vanishing point, with no drawings:
134 jevois::RawImage visual; // unallocated pixels, will not draw anything
135 itsRoadFinder->process(imggray, visual);
136
137 // Get the vanishing point and send to serial:
138 int const w = imggray.cols;
139 std::pair<Point2D<int>, float> vp = itsRoadFinder->getCurrVanishingPoint();
140 if (vp.second >= vpconf::get()) sendSerialImg1Dx(w, vp.first.i, 0.0F, "vp");
141 }
142
143 // ####################################################################################################
144 //! Processing function with USB video out
145 // ####################################################################################################
146 virtual void process(jevois::InputFrame && inframe, jevois::OutputFrame && outframe) override
147 {
148 // Wait for next available camera image:
149 jevois::RawImage inimg = inframe.get(); unsigned int const w = inimg.width, h = inimg.height;
150 inimg.require("input", w, h, V4L2_PIX_FMT_YUYV); // accept any image size but require YUYV pixels
151
153
154 // Convert it to gray:
155 cv::Mat imggray = jevois::rawimage::convertToCvGray(inimg);
156
157 // Compute the vanishing point. Note: the results will be drawn into inimg, so that we don't have to wait for
158 // outimg to be ready. It's ok to modify the input image, its buffer will be sent back to the camera driver for
159 // capture once we are done here, and will be overwritten anyway:
160 itsRoadFinder->process(imggray, inimg);
161
162 // Wait for an image from our gadget driver into which we will put our results:
163 jevois::RawImage outimg = outframe.get();
164
165 // Enforce the correct output image size and format:
166 outimg.require("output", w, h + 16, V4L2_PIX_FMT_YUYV);
167
168 // Paste the original image + drawings to the top-left corner of the display:
169 unsigned short const txtcol = 0xa0ff; //WHITE: 0x80ff;
170 jevois::rawimage::paste(inimg, outimg, 0, 0);
171 jevois::rawimage::writeText(outimg, "JeVois Road Navigation Demo", 3, 3, txtcol);
172
173 // Let camera know we are done processing the raw YUV input image:
174 inframe.done();
175
176 // Clear out the bottom section of the image:
178
179 // Get the vanishing point and send to serial:
180 std::pair<Point2D<int>, float> vp = itsRoadFinder->getCurrVanishingPoint();
181 if (vp.second >= vpconf::get()) sendSerialImg1Dx(w, vp.first.i, 0.0F, "vp");
182
183 // Write some extra info about the vp:
184 std::ostringstream otxt; otxt << std::fixed << std::setprecision(3);
185 otxt << "VP x=" << vp.first.i << " (" << vp.second << ") CTR=" << std::setprecision(1);
186 auto cp = itsRoadFinder->getCurrCenterPoint();
187 auto tp = itsRoadFinder->getCurrTargetPoint();
188 float const tpx = itsRoadFinder->getFilteredTargetX();
189 otxt << cp.i << " TGT=" << tp.i << " fTPX=" << tpx;
190 jevois::rawimage::writeText(outimg, otxt.str().c_str(), 3, h + 3, jevois::yuyv::White);
191
192 // Show processing fps:
193 std::string const & fpscpu = itsProcessingTimer.stop();
194 jevois::rawimage::writeText(outimg, fpscpu, 3, h - 13, jevois::yuyv::White);
195
196 // Send the output image with our processing results to the host over USB:
197 outframe.send();
198 }
199
200 // ####################################################################################################
201 //! Module internals
202 // ####################################################################################################
203 protected:
205 std::shared_ptr<RoadFinder> itsRoadFinder;
206};
207
208// Allow the module to be loaded as a shared object (.so) file:
JEVOIS_REGISTER_MODULE(ArUcoBlob)
int h
Road finder demo.
jevois::Timer itsProcessingTimer
Module internals.
virtual ~RoadNavigation()
Virtual destructor for safe inheritance.
virtual void process(jevois::InputFrame &&inframe, jevois::OutputFrame &&outframe) override
Processing function with USB video out.
std::shared_ptr< RoadFinder > itsRoadFinder
JEVOIS_DECLARE_PARAMETER(vpconf, float, "Minimum vanishing point confidence required to send a serial message. " "Note that currently, confidence values are binary (only 0 or 1), and quite conservative " "(many good detections may get a confidence of 0 if they are not very clean).", 0.0F, roadfinder::ParamCateg)
Parameter.
virtual void process(jevois::InputFrame &&inframe) override
Processing function, no video out.
RoadNavigation(std::string const &instance)
Constructor.
unsigned int width
unsigned int height
void require(char const *info, unsigned int w, unsigned int h, unsigned int f) const
StdModule(std::string const &instance)
void sendSerialImg1Dx(unsigned int camw, float x, float size=0.0F, std::string const &id="", std::string const &extra="")
std::string const & stop(double *seconds)
void paste(RawImage const &src, RawImage &dest, int dx, int dy)
void writeText(RawImage &img, std::string const &txt, int x, int y, unsigned int col, Font font=Font6x10)
cv::Mat convertToCvGray(RawImage const &src)
void drawFilledRect(RawImage &img, int x, int y, unsigned int w, unsigned int h, unsigned int col)
unsigned short constexpr Black
unsigned short constexpr White