qt 嵌入pcl窗口可视化点云:
先来个总结:工作需要完成QT + pcl可视化点云,本文分别介绍了不同版本之间搭配安装所踩的坑,如果你的电脑系统比较新,安装的系统插件比较少,那应该还是可以很快装完的,本文主要详细介绍在高版本的QT的情况下其余插件的安装情况和遇到的坑,如果你装不成功,Don’t give up,你需要的只是一个纯净的系统而已!因为原来装了很多软件的系统有些依赖或者库可能版本不太对应。第一次成功是老电脑的虚拟机上,在各个插件都是低版本的情况下很容易的就装成功了。 话不多说,来看过程:
搭配1安装过程(比较纯净的Ubuntu16.04 + QT5.5 + vtk6.2 +PCL1.7 + boost1.57 )
这个搭配没啥好说的,有很多教程,依赖库都用apt-get就可以了,跟着教程走基本没啥问题。QT的话应该安装qt5.5版本及以前版本的,因为qt5.6版本以后,qt将QWebKit模块改成了QWebEngine,在VTK库和PCL库编译的时候都要用到这个模块, 所以低版本兄弟们的参考其余博客的经验很快就好了。总结:在低版本的QT下,Ubuntu16.04 环境问题很容易解决,可以运行demo程序但是根据别的博客经验会有一些pcl的算法库不完整,建议使用源码编译安装;
搭配2 安装过程(Ubuntu16.04 + QT5.11.3 + VTK7.1.1/VTK8.2.0 + PCL1.8.1 )
这个搭配坑就比较多原因就在pcl 上,因为pcl 依赖boost ,本人在以前的工作中安装了Boost1.67,就导致后续的一系列问题,先上过程:
1、QT:5.11.3
直接下载安装https://download.qt.io/archive/qt/
QT安装步骤和环境变量的配置就不赘述了,网上有很多。
想要在qt中实现可视化点云,就需要QVTKWigdet控件,这个控件是由vtk库编译而来的。接下来就说VTK库的安装。
先来依赖库:
sudo apt-get update
sudo apt-get install git build-essential linux-libc-dev
sudo apt-get install cmake cmake-gui
sudo apt-get install libusb-1.0-0-dev libusb-dev libudev-dev
sudo apt-get install mpi-default-dev openmpi-bin openmpi-common
sudo apt-get install libflann1.8 libflann-dev
sudo apt-get install libeigen3-dev
sudo apt-get install libboost-all-dev
sudo apt-get install libqhull* libgtest-dev
sudo apt-get install freeglut3-dev pkg-config
sudo apt-get install libxmu-dev libxi-dev
sudo apt-get install mono-complete
sudo apt-get install libopenni-dev
sudo apt-get install libopenni2-dev
sudo apt-get install libx11-dev libxext-dev libxtst-dev libxrender-dev libxmu-dev libxmuu-dev
sudo apt-get install build-essential libgl1-mesa-dev libglu1-mesa-dev
sudo apt-get install cmake cmake-gui
2、VTK: vtk7.1.1(8.2.0也可以)
VTK 自己获取吧
下载、解压到本地然后
cd VTK-7.1.1/
mkdir build
cd build
cmake -DVTK_QT_VERSION:STRING=5 \
-DQT_QMAKE_EXECUTABLE:PATH=/home/alv/Qt5.11.3/5.11.3/gcc_64/bin/qmake \
-DVTK_Group_Qt:BOOL=ON \
-DCMAKE_PREFIX_PATH:PATH=/home/alv/Qt5.11.3/5.11.3/gcc_64/lib/cmake \
-DBUILD_SHARED_LIBS:BOOL=ON \
/home/alv/software/VTK/VTK-7.1.1 //注意根据自己的实际情况更改QT路径和VTK的路径
make -j4
Sudo make install
到这差不多也就编译好了,如果报cmake 的错误可以看下面的踩坑介绍
/****************************************************************************/
编译VTK的库最主要的原因还是需要libQVTKWidgetPlugin.so库文件,路径为/home/username/VTK-7.1.1/build/lib。讲这个文件复制到~/Qt5.11.3/Tools/QtCreator/lib/Qt/plugins/designer (如果你的QT版本不一样这个位置可能会不一样,有些QT需要放到QTXXX/Tools/QtCreator/bin/plugins/designer中)
此时打开QT的UI界面,便会出现QVTK的控件。
3、PCL库的安装
自己下载吧:https://github.com/PointCloudLibrary/pcl/releases
PCL(Point Cloud Library )点云库是一个开源的c++代码库,包含了大量的点云相关的通用算法和数据结构。在SLAM领域有着广泛的应用,官方的安装教程
sudo add-apt-repository ppa:v-launchpad-jochen-sprickerhof-de/pcl
sudo apt-get update
sudo apt-get install libpcl-all
上面那种安装方法会出现无法定位到libpcl-all package的问题,因此最最保守的是要采用源码安装方式,本人就踩坑了,装好QT + VTK后已经在QT中设置好了QVTKWidegt并编译成功,但是在运行的时候却运行不起来,最后单步调试了好久才定位到PCL的库上。
下载pcl库的源码。同样的方法,建build文件夹,cd pcl-1.8.1
mkdir build
cd build
cmake -DCMAKE_BUILD_TYPE=None -DCMAKE_INSTALL_PREFIX=/usr \
-DBUILD_GPU=ON -DBUILD_apps=ON -DBUILD_examples=ON \
-DCMAKE_INSTALL_PREFIX=/usr ..
make -j4
sudo make install
一般来说如果你的系统比较干净的话,一条龙直接就装好了,如果没装好,缺啥装啥,下面是本人遇到的几个大坑,介绍一下解决办法;
下面来一个demo :
.pro
#Eigen
INCLUDEPATH += /usr/include/eigen3
#Boost
INCLUDEPATH += /usr/include/boost
LIBS += /usr/lib/x86_64-linux-gnu/libboost_*.so
#Vtk
INCLUDEPATH += /usr/local/include/vtk-7.1
LIBS +=/usr/local/lib/libvtk*.so
#PCL Header
#INCLUDEPATH += /usr/local/include/pcl-1.8
INCLUDEPATH += /usr/include/pcl-1.8/
#PCL Lib
#LIBS += /usr/local/lib/libpcl_*.so \
LIBS +=/usr/lib/libpcl_*.so
pclview.h
#pragma once
#include <iostream>
// Qt
#include <QMainWindow>
// Point Cloud Library
#include <pcl/point_cloud.h>
#include <pcl/point_types.h>
#include <pcl/visualization/pcl_visualizer.h>
// Visualization Toolkit (VTK)
#include <vtkRenderWindow.h>
typedef pcl::PointXYZRGBA PointT;
typedef pcl::PointCloud<PointT> PointCloudT;
namespace Ui
{
class PCLViewer;
}
class PCLViewer : public QMainWindow
{
Q_OBJECT
public:
explicit PCLViewer (QWidget *parent = nullptr);
~PCLViewer ();
public Q_SLOTS:
void
randomButtonPressed ();
void
RGBsliderReleased ();
void
pSliderValueChanged (int value);
void
redSliderValueChanged (int value);
void
greenSliderValueChanged (int value);
void
blueSliderValueChanged (int value);
protected:
pcl::visualization::PCLVisualizer::Ptr viewer;
PointCloudT::Ptr cloud;
unsigned int red;
unsigned int green;
unsigned int blue;
private:
Ui::PCLViewer *ui;
};
main .cpp
#include "pclviewer.h"
#include <QApplication>
#include <QMainWindow>
int main (int argc, char *argv[])
{
QApplication a (argc, argv);
PCLViewer w;
w.show ();
return a.exec ();
}
pclviewer.cpp
#include "pclviewer.h"
#include "ui_pclviewer.h"
PCLViewer::PCLViewer (QWidget *parent) :
QMainWindow (parent),
ui (new Ui::PCLViewer)
{
ui->setupUi (this);
this->setWindowTitle ("PCL viewer");
// Setup the cloud pointer
cloud.reset (new PointCloudT);
// The number of points in the cloud
cloud->points.resize (200);
// The default color
red = 128;
green = 128;
blue = 128;
// Fill the cloud with some points
for (size_t i = 0; i < cloud->points.size (); ++i)
{
cloud->points[i].x = 1024 * rand () / (RAND_MAX + 1.0f);
cloud->points[i].y = 1024 * rand () / (RAND_MAX + 1.0f);
cloud->points[i].z = 1024 * rand () / (RAND_MAX + 1.0f);
cloud->points[i].r = red;
cloud->points[i].g = green;
cloud->points[i].b = blue;
}
// Set up the QVTK window
viewer.reset (new pcl::visualization::PCLVisualizer ("viewer", false));
ui->qvtkWidget->SetRenderWindow (viewer->getRenderWindow ());
viewer->setupInteractor (ui->qvtkWidget->GetInteractor (), ui->qvtkWidget->GetRenderWindow ());
ui->qvtkWidget->update ();
// Connect "random" button and the function
connect (ui->pushButton_random, SIGNAL (clicked ()), this, SLOT (randomButtonPressed ()));
// Connect R,G,B sliders and their functions
connect (ui->horizontalSlider_R, SIGNAL (valueChanged (int)), this, SLOT (redSliderValueChanged (int)));
connect (ui->horizontalSlider_G, SIGNAL (valueChanged (int)), this, SLOT (greenSliderValueChanged (int)));
connect (ui->horizontalSlider_B, SIGNAL (valueChanged (int)), this, SLOT (blueSliderValueChanged (int)));
connect (ui->horizontalSlider_R, SIGNAL (sliderReleased ()), this, SLOT (RGBsliderReleased ()));
connect (ui->horizontalSlider_G, SIGNAL (sliderReleased ()), this, SLOT (RGBsliderReleased ()));
connect (ui->horizontalSlider_B, SIGNAL (sliderReleased ()), this, SLOT (RGBsliderReleased ()));
// Connect point size slider
connect (ui->horizontalSlider_p, SIGNAL (valueChanged (int)), this, SLOT (pSliderValueChanged (int)));
viewer->addPointCloud (cloud, "cloud");
pSliderValueChanged (2);
viewer->resetCamera ();
ui->qvtkWidget->update ();
}
void
PCLViewer::randomButtonPressed ()
{
printf ("Random button was pressed\n");
// Set the new color
for (size_t i = 0; i < cloud->size(); i++)
{
cloud->points[i].r = 255 *(1024 * rand () / (RAND_MAX + 1.0f));
cloud->points[i].g = 255 *(1024 * rand () / (RAND_MAX + 1.0f));
cloud->points[i].b = 255 *(1024 * rand () / (RAND_MAX + 1.0f));
}
viewer->updatePointCloud (cloud, "cloud");
ui->qvtkWidget->update ();
}
void
PCLViewer::RGBsliderReleased ()
{
// Set the new color
for (size_t i = 0; i < cloud->size (); i++)
{
cloud->points[i].r = red;
cloud->points[i].g = green;
cloud->points[i].b = blue;
}
viewer->updatePointCloud (cloud, "cloud");
ui->qvtkWidget->update ();
}
void
PCLViewer::pSliderValueChanged (int value)
{
viewer->setPointCloudRenderingProperties (pcl::visualization::PCL_VISUALIZER_POINT_SIZE, value, "cloud");
ui->qvtkWidget->update ();
}
void
PCLViewer::redSliderValueChanged (int value)
{
red = value;
printf ("redSliderValueChanged: [%d|%d|%d]\n", red, green, blue);
}
void
PCLViewer::greenSliderValueChanged (int value)
{
green = value;
printf ("greenSliderValueChanged: [%d|%d|%d]\n", red, green, blue);
}
void
PCLViewer::blueSliderValueChanged (int value)
{
blue = value;
printf("blueSliderValueChanged: [%d|%d|%d]\n", red, green, blue);
}
PCLViewer::~PCLViewer ()
{
delete ui;
}
pclviewer.ui 如下图所示
这是官方的一个demo,后续如果如果有时间会上传完整的工程文件,来个运行结果图
结果差不多如图,下面来介绍一下安装过程中遇到的坑吧,希望搞大家一点帮助;
安装过程遇到的坑
1、pcl 依赖boost的坑
先上下载链接https://www.boost.org/users/history/
pcl 依赖boost ,本人以前装了boost1.67,导致编译报错,一看是cmake的原因, ubuntu 16.04 默认安装的 cmake 版本为 3.5,但有时编译一些包时需要更高的版本,所以需要升级一下 cmake。因为CMake无法检测不同Boost库之间的依赖关系。他们明确地实施了FindBoost。对于每个Boost版本,这些信息都由CMake维护者添加,它将成为下一个CMake版本的一部分。因此,您必须确保您的CMake版本在您尝试查找的Boost版本之后发布。问题来了,本人升级了cmake 至3.13版本,boost 1.67过了但是VTK报错,原因是cmake 版本太高,头疼,最后尝试了3.12还是报错后,果断卸载BOOST1.67. 换回 低版本的boost,下面是boost 版本和cmake之间的关系:
Boost 1.63要求CMake 3.7或更高版本。
Boost 1.64需要CMake 3.8或更高版本。
升压1.65和1.65.1需要CMake 3.9.3或更高版本。
Boost 1.66需要CMake 3.11或更高版本。
Boost 1.67需要CMake 3.12或更高版本。
升压1.68,1.69要求CMake 3.13或更高版本。
Boost 1.70需要CMake 3.14或更高版本。
查看boost 版本
dpkg -S /usr/include/boost/version.hpp
如果编译好程序后,在运行时提示无法加载某个库文件,则把/usr/local/lib下的所有boost的库文件mv到/usr/lib目录下就可以了。
默认安装头文件在目录/usr/local/include,而库文件在目录/usr/local/lib。卸载也很简单,直接将以上两个目录中有关boost的内容删除就可以了。
2、cmake 升级的坑
若用 cmake 编译过 ros ,千万别傻乎乎地随便找个帖子执行下面的命令:
sudo apt-get autoremove cmake
这样会把之前用 cmake 编译好的包都给卸载掉。
比较简单的方法是下载 cmake 压缩包,直接建立软链接覆盖掉系统的 cmake,
cd ~/Download
wget https://cmake.org/files/v3.13/cmake-3.13.0-Linux-x86_64.tar.gz
tar -xzvf cmake-3.13.0-Linux-x86_64.tar.gz
解压出来的包,将其放在 /opt 目录下,其他目录也可以,主要别以后不小心删了
sudo mv cmake-3.13.0-Linux-x86_64 /opt/cmake-3.13.0
#建立软链接
sudo ln -sf /opt/cmake-3.13.0/bin/* /usr/bin/
#查看 cmake 版本
cmake --version
3、一种不升级cmake 也能解决boost 版本问题的办法
使用新版本的boost库,运行cmake编译程序时,遇到警告信息: Imported targets not available for Boost version 106700,
这是由于cmake版本旧,boost版本新,cmake带来的FindBoost.cmake,
编辑/usr/share/cmake-3.5/Modules/FindBoost.cmake文件,搜索Imported targets not available for Boost version ${Boost_VERSION}
在这个if语句最后加入,内容可以复制对上个版本的内容或者把版本好加大:
elseif(NOT Boost_VERSION VERSION_LESS 106700 AND Boost_VERSION VERSION_LESS 106800)
set(_Boost_CHRONO_DEPENDENCIES system)
set(_Boost_CONTEXT_DEPENDENCIES thread chrono system date_time)
set(_Boost_COROUTINE_DEPENDENCIES context system)
set(_Boost_FIBER_DEPENDENCIES context thread chrono system date_time)
set(_Boost_FILESYSTEM_DEPENDENCIES system)
set(_Boost_IOSTREAMS_DEPENDENCIES regex)
set(_Boost_LOG_DEPENDENCIES date_time log_setup system filesystem thread regex chrono atomic)
set(_Boost_MATH_DEPENDENCIES math_c99 math_c99f math_c99l math_tr1 math_tr1f math_tr1l atomic)
set(_Boost_MPI_DEPENDENCIES serialization)
set(_Boost_MPI_PYTHON_DEPENDENCIES python mpi serialization)
set(_Boost_RANDOM_DEPENDENCIES system)
set(_Boost_THREAD_DEPENDENCIES chrono system date_time atomic)
set(_Boost_WAVE_DEPENDENCIES filesystem system serialization thread chrono date_time atomic)
set(_Boost_WSERIALIZATION_DEPENDENCIES serialization)
else()
message(WARNING "Imported targets not available for Boost version ${Boost_VERSION}")
set(_Boost_IMPORTED_TARGETS FALSE)
endif()
最后
来个链接吧,上面大部分时间如果没有采用科学的上网方式,下载速度还是很慢的,这里有本人上面提到的工具包pcl_vtk_cmake各个版本全套包.tar.gz