- iOS/Objective-C 元类和类别
- objective-c - -1001 错误,当 NSURLSession 通过 httpproxy 和/etc/hosts
- java - 使用网络类获取 url 地址
- ios - 推送通知中不播放声音
我正在尝试将带有 rgb 信息的点云从 pcl 格式转换为 cv::Mat,然后再转换回 pcl。我找到了 convert mat to pointcloud在 stackoverflow 上。
代码已更新
因此,我使用在 stackoverflow 上找到的代码作为起点。现在有以下内容:
//input pcl::PointCloud<pcl::PointXYZRGB> point_cloud_ptr
cv::Mat OpenCVPointCloud(3, point_cloud_ptr.points.size(), CV_64FC1);
OpenCVPointCloudColor = cv::Mat(480, 640, CV_8UC3);
for(int y=0;y<OpenCVPointCloudColor.rows;y++)
{
for(int x=0;x<OpenCVPointCloudColor.cols;x++)
{
OpenCVPointCloud.at<double>(0,y*OpenCVPointCloudColor.cols+x) = point_cloud_ptr.points.at(y*OpenCVPointCloudColor.cols+x).x;
OpenCVPointCloud.at<double>(1,y*OpenCVPointCloudColor.cols+x) = point_cloud_ptr.points.at(y*OpenCVPointCloudColor.cols+x).y;
OpenCVPointCloud.at<double>(2,y*OpenCVPointCloudColor.cols+x) = point_cloud_ptr.points.at(y*OpenCVPointCloudColor.cols+x).z;
cv::Vec3b color = cv::Vec3b(point_cloud_ptr.points.at(y*OpenCVPointCloudColor.cols+x).b,point_cloud_ptr.points.at(y*OpenCVPointCloudColor.cols+x).g,point_cloud_ptr.points.at(y*OpenCVPointCloudColor.cols+x).r);
OpenCVPointCloudColor.at<cv::Vec3b>(cv::Point(x,y)) = color;
}
}
cv::imshow("view 2", OpenCVPointCloudColor);
cv::waitKey(30);
显示上面的图像确保我正确提取了颜色(通过肉眼将图像与原始图像进行比较)。然后我想将它转换回点云:
pcl::PointCloud<pcl::PointXYZRGB>::Ptr point_cloud_ptr(new pcl::PointCloud<pcl::PointXYZRGB>);
for(int y=0;y<OpenCVPointCloudColor.rows;y++)
{
for(int x=0;x<OpenCVPointCloudColor.cols;x++)
{
pcl::PointXYZRGB point;
point.x = OpencVPointCloud.at<double>(0,y*OpenCVPointCloudColor.cols+x);
point.y = OpencVPointCloud.at<double>(1,y*OpenCVPointCloudColor.cols+x);
point.z = OpencVPointCloud.at<double>(2,y*OpenCVPointCloudColor.cols+x);
cv::Vec3b color = OpenCVPointCloudColor.at<cv::Vec3b>(cv::Point(x,y));
//Try 1 not working
//uint8_t r = (color[2]);
//uint8_t g = (color[1]);
//uint8_t b = (color[0]);
//Try 2 not working
//point.r = color[2];
//point.g = color[1];
//point.b = color[0];
//Try 3 not working
//uint8_t r = (color.val[2]);
//uint8_t g = (color.val[1]);
//uint8_t b = (color.val[0]);
//test working WHY DO THE ABOVE CODES NOT WORK :/
uint8_t r = 255;
uint8_t g = 0;
uint8_t b = 0;
int32_t rgb = (r << 16) | (g << 8) | b;
point.rgb = *reinterpret_cast<float*>(&rgb);
point_cloud_ptr -> points.push_back(point);
}
}
谁能解释为什么明确指定 255,0,0 的值会把所有东西都染成红色。但是如果我选择彩色图像的输出,云的颜色是错误的吗?
偶然发现this ,除了云类型不同之外,我看不出我的代码有什么不同?
更新
读书this关于 PCL 的讨论以我切换到 xyzrgba 结束(也在 stackoverflow 中提到)。我在转换回来时尝试的代码是:
point.b = OpenCVPointCloudColor.at<cv::Vec3b>(x,y)[0];
point.g = OpenCVPointCloudColor.at<cv::Vec3b>(x,y)[1];
point.r = OpenCVPointCloudColor.at<cv::Vec3b>(x,y)[2];
point.a = 255;
生成的颜色云与 XYZRGB 中创建的颜色云不同,但仍然是错误的:/WTF?
额外
即使我在所有点中强制使用红色 OpenCVPointCloudColor
使用 cvCloudColor.at<cv::Vec3f>(x,y) = cv::Vec3f(0,0,255);
然后从 OpenCVPointCloudColor
读取仍然在 pcl 云中创建错误的颜色信息。
最佳答案
我几乎可以肯定您的代码中围绕这些函数的某处存在错误。我按照你的范例尝试了简单的例子,它完美地工作(从源代码构建的 PCL 1.8,从源代码构建的 OpenCV 3.1,g++ 5.x 或 g++ 6.x,Ubuntu 16.10):
#include <pcl/visualization/cloud_viewer.h>
#include <opencv2/core.hpp>
#include <opencv2/imgproc.hpp>
#include <opencv2/highgui.hpp>
void draw_cloud(
const std::string &text,
const pcl::PointCloud<pcl::PointXYZRGB>::Ptr &cloud)
{
pcl::visualization::CloudViewer viewer(text);
viewer.showCloud(cloud);
while (!viewer.wasStopped())
{
}
}
pcl::PointCloud<pcl::PointXYZRGB>::Ptr img_to_cloud(
const cv::Mat& image,
const cv::Mat &coords)
{
pcl::PointCloud<pcl::PointXYZRGB>::Ptr cloud(new pcl::PointCloud<pcl::PointXYZRGB>());
for (int y=0;y<image.rows;y++)
{
for (int x=0;x<image.cols;x++)
{
pcl::PointXYZRGB point;
point.x = coords.at<double>(0,y*image.cols+x);
point.y = coords.at<double>(1,y*image.cols+x);
point.z = coords.at<double>(2,y*image.cols+x);
cv::Vec3b color = image.at<cv::Vec3b>(cv::Point(x,y));
uint8_t r = (color[2]);
uint8_t g = (color[1]);
uint8_t b = (color[0]);
int32_t rgb = (r << 16) | (g << 8) | b;
point.rgb = *reinterpret_cast<float*>(&rgb);
cloud->points.push_back(point);
}
}
return cloud;
}
void cloud_to_img(
const pcl::PointCloud<pcl::PointXYZRGB>::Ptr &cloud,
cv::Mat &coords,
cv::Mat &image)
{
coords = cv::Mat(3, cloud->points.size(), CV_64FC1);
image = cv::Mat(480, 640, CV_8UC3);
for(int y=0;y<image.rows;y++)
{
for(int x=0;x<image.cols;x++)
{
coords.at<double>(0,y*image.cols+x) = cloud->points.at(y*image.cols+x).x;
coords.at<double>(1,y*image.cols+x) = cloud->points.at(y*image.cols+x).y;
coords.at<double>(2,y*image.cols+x) = cloud->points.at(y*image.cols+x).z;
cv::Vec3b color = cv::Vec3b(
cloud->points.at(y*image.cols+x).b,
cloud->points.at(y*image.cols+x).g,
cloud->points.at(y*image.cols+x).r);
image.at<cv::Vec3b>(cv::Point(x,y)) = color;
}
}
}
int main(int argc, char *argv[])
{
cv::Mat image = cv::imread("test.png");
cv::resize(image, image, cv::Size(640, 480));
cv::imshow("initial", image);
cv::Mat coords(3, image.cols * image.rows, CV_64FC1);
for (int col = 0; col < coords.cols; ++col)
{
coords.at<double>(0, col) = col % image.cols;
coords.at<double>(1, col) = col / image.cols;
coords.at<double>(2, col) = 10;
}
pcl::PointCloud<pcl::PointXYZRGB>::Ptr cloud = img_to_cloud(image, coords);
draw_cloud("points", cloud);
cloud_to_img(cloud, coords, image);
cv::imshow("returned", image);
cv::waitKey();
return 0;
}
“初始”和“返回”图像完全相同。在 PCL 的查看器中,我将我的图像视为点云,当然,z = 10,因为我对其进行了硬编码。您可能应该使用鼠标滚轮来缩小并查看整个图像。
要运行此示例,您的工作目录中应该有名为“test.png”的文件。
我很抱歉硬编码输入文件名并调整到固定分辨率。
尝试一下,如果它在您的系统中有效,请尝试在您的代码中查找错误。如果它不起作用,则可能是您的 PCL 版本太旧甚至损坏。
关于c++ - 如何将 cv::Mat 转换为带颜色的 pcl::pointcloud,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41816369/
我想知道这是否可能。我有一个功能: pcl::PointCloud createPointCloud(std::Vector input) 返回一个点云。我想知道是否可以获取这个点云,并制作一个指向
我有两个 PointCloud 对象,每个对象对应一个特定的结构和纹理。一个应该是可点击的,但另一个不是。我们分别称它们为 P1 和 P2。 P1 使用 THREE.ShaderMaterial 初始
我正在尝试: 绘制一个 THREE.PointCloud 对象,大约。 150k 点,其中点从网络应用程序发送。 缩放 THREE.PointCloud 对象中的点以获得类似于此的结果(使用 Maya
我想优化我的 OpenGL 程序。它包括加载 3D 点 vector ,然后对它们应用着色器。但是我有数十亿个点,当我尝试查看这些点时,我的 FPS 下降到 2。 实际上我正在发送每个点,我相信这对我
这很可能是一件简单的事情,但我被卡住了。我正在尝试在头文件中初始化点云库点云,以便我可以跨函数共享它。 我正在尝试: //.h typedef pcl::PointCloud PointCloud;
我在 three.js 的帮助下可视化 3d 数据点(我通过 csv 文件读取)。我想单击该 PointCloud 中的点以显示这些特定点的其他测量数据。根据例子,我发现这显然是可能的,但我没有让它工
我想通过它的置信度值对 PointCloud 进行着色。 首先,我创建了三个 FloatBuffer,我在其中放置基于阈值的单个点。 private FloatBuffer makeFLoatBuff
我正在使用库 PCL 读取 .pcd 点云。我需要提取这个点云的轮廓切割。关于如何实现此类功能的任何想法建议? 基本上,我想沿着点云移动一个盒子,并将盒子中存在的点投影到一个平面上。 我已经完成了点云
所以我有这段代码,我在其中尝试使用点云库来匹配我之前计算的一些描述符和其他描述符: pcl::KdTreeFLANN matching = new pcl::KdTreeFLANN(false); p
假设我初始化了一个点云。我想将其 RGB channel 存储在 opencv 的 Mat 数据类型中。我该怎么做? pcl::PointCloud::Ptr cloud (new pcl::Poin
我在 HelixToolKit 中创建了一个点云。我需要为每个点应用颜色。当我使用 PointVisual3D 时,没有为每个点设置颜色的选项。它为整个点云设置颜色。当我在 Helix 工具包中使用
我在为在 Scene3d 中显示点云而编写的 QML 应用程序中发现了主要性能问题。 1000 点/秒没问题,但在 10,000 点时它基本上只会让我的整个计算机停止运行。目标是达到数百万点(这是旧应
我正在尝试使用 ShaderMaterial 在单个 PointCloud 中使用多个纹理。我将纹理数组连同纹理索引属性一起传递给着色器,并选择要在片段着色器中使用的适当纹理。 相关设置代码: var
我正在使用 PLYLoader 加载一个 .ply 文件,并使用 three.js 中的 PointCloud 对象渲染它。 var loader = new THREE.PLYLoader(); l
我正在尝试从 this 运行 ICP 算法 header 。第 260 行的函数声明为 template void point_to_point(Eigen::MatrixBase& X,
我最近开始尝试使用 Three.js。我尝试使用 PointCloud 对象创建椭圆体粒子云。 我使用椭圆体的参数方程生成随机点,如下所示: var vertex = new THREE.Ve
如何从 opencv Mat 点云到 pcl::pointcloud?颜色对我来说并不重要,重要的是点本身。 最佳答案 你可以这样做: pcl::PointCloud::Ptr SimpleOpenN
我是 PCL 的新手。我正在使用 PCL 库,我正在寻找一种从点云中提取点或将特定点复制到新点的方法。我想验证每个点是否符合条件,我想获得一个只有好的点的点云。谢谢! 最佳答案 使用 ExtractI
我正在尝试将带有 rgb 信息的点云从 pcl 格式转换为 cv::Mat,然后再转换回 pcl。我找到了 convert mat to pointcloud在 stackoverflow 上。 代码
我正在将此深度图像转换为 pcl::pointcloud。 使用以下内容: PointCloud::Ptr PointcloudUtils::RGBDtoPCL(cv::Mat depth_image
我是一名优秀的程序员,十分优秀!