【CUDA-BEVFusion】可视化源文件src/common/visualize.cu (二)

CUDA-BEVFusion中,src/common/visualize.cu 源文件的当前部分代码class BEVArtistImplement主要作用是**将3D点云数据和3D边界框(Bounding Box)投影到2D图像平面,并在图像上进行可视化。

一、src/common/visualize.cu 部分源码

// 定义half5结构体,用于存储5个half类型的值
typedef struct {
   
  half val[5];
} half5;

// 限制函数:将value限制在[amin, amax]范围内
template <typename _T>
static __host__ __device__ _T limit(_T value, _T amin, _T amax) {
   
  return value < amin ? amin : (value > amax ? amax : value);
}

// CUDA核函数:将点云数据投影到图像上并绘制
static __global__ void draw_point_to(unsigned int num, const half5* points, float4* view_port, unsigned char* image,
                                     int image_width, int stride, int image_height) {
   
  unsigned int idx = cuda_linear_index; // 获取当前线程的全局索引
  if (idx >= num) return; // 如果索引超出点云数量,直接返回

  half5 point = points[idx]; // 获取当前点
  float px = point.val[0]; // 点的x坐标
  float py = point.val[1]; // 点的y坐标
  float pz = point.val[2]; // 点的z坐标
  float reflection = point.val[3]; // 反射率(未使用)
  float indensity = point.val[4]; // 强度(未使用)

  // 获取视口变换矩阵的行
  float4 r0 = view_port[0];
  float4 r1 = view_port[1];
  float4 r2 = view_port[2];

  // 将3D点投影到图像平面
  float x = px * r0.x + py * r0.y + pz * r0.z + r0.w;
  float y = px * r1.x + py * r1.y + pz * r1.z + r1.w;
  float w = px * r2.x + py * r2.y + pz * r2.z + r2.w;

  if (w <= 0) return; // 如果投影点在相机后方,直接返回

  x = x / w; // 归一化x坐标
  y = y / w; // 归一化y坐标

  // 检查投影点是否在图像范围内
  if (x < 0 || x >= image_width || y < 0 || y >= image_height) {
   
    return;
  }

  int ix = static_cast<int>(x); // 计算图像像素的x坐标
  int iy = static_cast<int>(y); // 计算图像像素的y坐标

  // 计算点的深度透明度
  float alpha = limit((pz + 5.0f) / 8.0f, 0.35f, 1.0f);
  unsigned char gray = limit(alpha * 255, 0.0f, 255.0f); // 将透明度转换为灰度值

  // 将灰度值写入图像
  *(uchar3*)&image[iy * stride + ix * 3] = make_uchar3(gray, gray, gray);
}

// Rodrigues旋转公式:根据旋转角度和旋转轴生成旋转矩阵
static std::vector<nvtype::Float4> rodrigues_rotation(float radian, const std::vector<float>& axis) {
   
  std::vector<nvtype::Float4> output(4); // 输出4x4旋转矩阵
  memset(&output[0], 0, output.size() * sizeof(nvtype::Float4)); // 初始化矩阵为0

  float nx = axis[0]; // 旋转轴x分量
  float ny = axis[1]; // 旋转轴y分量
  float nz = axis[2]; // 旋转轴z分量
  float cos_val = cos(radian); // 旋转角度的余弦值
  float sin_val = sin(radian); // 旋转角度的正弦值
  output[3].w = 1; // 设置矩阵的右下角为1

  float a = 1 - cos_val; // Rodrigues公式中的系数
  float identity[3][3] = {
    
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值