mainwindow.cpp 8.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295
  1. #include "mainwindow.h"
  2. #include "ui_mainwindow.h"
  3. static int BEAMNUM;
  4. static double STEP;
  5. static double MINFLOOR;
  6. static double MAXFLOOR;
  7. static double MAXCEILING;
  8. static double MINCEILING;
  9. static double ROADSLOPMINHEIGHT;
  10. static double ROADSLOPMAXHEIGHT;
  11. static double ROTATION;
  12. static double OBSTACLEMINHEIGHT;
  13. static double MAXBACKDISTANCE;
  14. static double PASSHEIGHT;
  15. static double MAXRANGE;
  16. static double MINRANGE;
  17. static double GRIDSIZE;
  18. static double IMAGESIZE;
  19. static bool SYNC;
  20. MainWindow::MainWindow(QWidget* parent)
  21. : QMainWindow(parent)
  22. #ifdef DEBUG_GUI
  23. , ui(new Ui::MainWindow)
  24. #endif
  25. {
  26. #ifdef DEBUG_GUI
  27. ui->setupUi(this);
  28. #endif
  29. ros::NodeHandle private_nh("~");
  30. private_nh.param("BEAMNUM", BEAMNUM, 1440);
  31. private_nh.param("STEP", STEP, 0.1);
  32. private_nh.param("MINFLOOR", MINFLOOR, -3.0);
  33. private_nh.param("MAXFLOOR", MAXFLOOR, -1.3);
  34. private_nh.param("MAXCEILING", MAXCEILING, 6.0);
  35. private_nh.param("MINCEILING", MINCEILING, -0.5);
  36. private_nh.param("ROADSLOPMINHEIGHT", ROADSLOPMINHEIGHT, 80.0);
  37. private_nh.param("ROADSLOPMAXHEIGHT", ROADSLOPMAXHEIGHT, 30.0);
  38. private_nh.param("ROTATION", ROTATION, (double)3);
  39. private_nh.param("OBSTACLEMINHEIGHT", OBSTACLEMINHEIGHT, (double)1);
  40. private_nh.param("MAXBACKDISTANCE", MAXBACKDISTANCE, (double)1);
  41. private_nh.param("PASSHEIGHT", PASSHEIGHT, (double)2);
  42. private_nh.param("MAXRANGE", MAXRANGE, 80.0);
  43. private_nh.param("MINRANGE", MINRANGE, (double)3);
  44. private_nh.param("GRIDSIZE", GRIDSIZE, 10.0);
  45. private_nh.param("IMAGESIZE", IMAGESIZE, 1000.0);
  46. private_nh.param("SYNC", SYNC, false);
  47. if (SYNC == false)
  48. {
  49. velodyne = new ROSSub<sensor_msgs::PointCloud2ConstPtr>("points_raw", 1000, 10);
  50. }
  51. else
  52. {
  53. velodyne = new ROSSub<sensor_msgs::PointCloud2ConstPtr>("/sync_drivers/points_raw", 1000, 10);
  54. }
  55. connect(velodyne, SIGNAL(receiveMessageSignal()), this, SLOT(generateVirtualScanSlot()));
  56. vsros = new ROSPub<sensor_msgs::PointCloud2>("/vscan_points", 1000);
  57. scanros = new ROSPub<sensor_msgs::LaserScan>("/scan", 1000);
  58. #ifdef DEBUG_GUI
  59. double PI = 3.141592654;
  60. double density = 2 * PI / BEAMNUM;
  61. for (int i = 0; i < BEAMNUM; i++)
  62. {
  63. ui->comboBox->insertItem(i, QString("%1").arg((i * density - PI) * 180.0 / PI));
  64. }
  65. ui->comboBox->insertItem(BEAMNUM, "NULL");
  66. connect(ui->comboBox, SIGNAL(currentIndexChanged(int)), this, SLOT(showMatrixSlot(int)));
  67. connect(ui->step, SIGNAL(valueChanged(double)), this, SLOT(recalculateSlot()));
  68. connect(ui->rotation, SIGNAL(valueChanged(double)), this, SLOT(recalculateSlot()));
  69. connect(ui->minrange, SIGNAL(valueChanged(double)), this, SLOT(recalculateSlot()));
  70. ui->label->resize(IMAGESIZE, IMAGESIZE);
  71. image = QImage(IMAGESIZE, IMAGESIZE, QImage::Format_RGB888);
  72. drawGrid();
  73. #endif
  74. velodyne->startReceiveSlot();
  75. }
  76. MainWindow::~MainWindow()
  77. {
  78. velodyne->stopReceiveSlot();
  79. delete velodyne;
  80. delete vsros;
  81. delete scanros;
  82. #ifdef DEBUG_GUI
  83. delete ui;
  84. #endif
  85. }
  86. void MainWindow::generateVirtualScanSlot()
  87. {
  88. virtualscan.velodyne = velodyne->getMessage();
  89. recalculateSlot();
  90. }
  91. void MainWindow::showMatrixSlot(int beamid)
  92. {
  93. if (beamid >= BEAMNUM)
  94. {
  95. return;
  96. }
  97. ui->tableWidget->clear();
  98. int size = int((MAXCEILING - MINFLOOR) / STEP + 0.5);
  99. ui->tableWidget->setRowCount(size);
  100. ui->tableWidget->setColumnCount(5);
  101. for (int i = 0; i < size; i++)
  102. {
  103. ui->tableWidget->setVerticalHeaderItem(i, new QTableWidgetItem(QString("%1").arg(MINFLOOR + i * STEP)));
  104. }
  105. ui->tableWidget->setHorizontalHeaderLabels(QStringList() << "RotID"
  106. << "RotLength"
  107. << "RotHeight"
  108. << "Length"
  109. << "Height");
  110. for (int i = 0; i < size; i++)
  111. {
  112. ui->tableWidget->setItem(i, 0, new QTableWidgetItem(QString("%1").arg(virtualscan.svs[beamid][i].rotid)));
  113. ui->tableWidget->setItem(i, 1, new QTableWidgetItem(QString("%1").arg(virtualscan.svs[beamid][i].rotlength)));
  114. ui->tableWidget->setItem(i, 2, new QTableWidgetItem(QString("%1").arg(virtualscan.svs[beamid][i].rotheight)));
  115. ui->tableWidget->setItem(i, 3, new QTableWidgetItem(QString("%1").arg(virtualscan.svs[beamid][i].length)));
  116. ui->tableWidget->setItem(i, 4, new QTableWidgetItem(QString("%1").arg(virtualscan.svs[beamid][i].height)));
  117. }
  118. drawBeam(beamid);
  119. }
  120. void MainWindow::recalculateSlot()
  121. {
  122. double PI = 3.141592654;
  123. double density = 2 * PI / BEAMNUM;
  124. #ifdef DEBUG_GUI
  125. QTime start = QTime::currentTime();
  126. #endif
  127. virtualscan.calculateVirtualScans(BEAMNUM, STEP, MINFLOOR, MAXCEILING, OBSTACLEMINHEIGHT, MAXBACKDISTANCE,
  128. ROTATION * PI / 180.0, MINRANGE);
  129. #ifdef DEBUG_GUI
  130. QTime end = QTime::currentTime();
  131. #endif
  132. virtualscan.getVirtualScan(ROADSLOPMINHEIGHT * PI / 180.0, ROADSLOPMAXHEIGHT * PI / 180.0, MAXFLOOR, MINCEILING,
  133. PASSHEIGHT, beams);
  134. #ifdef DEBUG_GUI
  135. ui->tc->setText(QString("%1").arg(start.msecsTo(end)));
  136. #endif
  137. {
  138. sensor_msgs::PointCloud2 msg;
  139. msg.header = virtualscan.velodyne->header;
  140. msg.fields = virtualscan.velodyne->fields;
  141. msg.height = 2;
  142. msg.width = BEAMNUM;
  143. msg.point_step = 8 * sizeof(float);
  144. msg.row_step = msg.width * msg.point_step;
  145. msg.data.resize(msg.height * msg.width * msg.point_step);
  146. unsigned char* base = msg.data.data();
  147. for (int i = 0; i < BEAMNUM; i++)
  148. {
  149. double theta = i * density - PI;
  150. float* data;
  151. int* ring;
  152. data = (float*)(base + (2 * i) * msg.point_step);
  153. data[0] = beams[i] * cos(theta);
  154. data[1] = beams[i] * sin(theta);
  155. data[2] = virtualscan.minheights[i];
  156. data[4] = 255;
  157. ring = (int*)(data + 5 * sizeof(float));
  158. *ring = 0;
  159. data = (float*)(base + (2 * i + 1) * msg.point_step);
  160. data[0] = beams[i] * cos(theta);
  161. data[1] = beams[i] * sin(theta);
  162. data[2] = virtualscan.maxheights[i];
  163. data[4] = 255;
  164. ring = (int*)(data + 5 * sizeof(float));
  165. *ring = 1;
  166. }
  167. vsros->sendMessage(msg);
  168. }
  169. {
  170. sensor_msgs::LaserScan msg;
  171. msg.header.frame_id = virtualscan.velodyne->header.frame_id;
  172. msg.header.seq = virtualscan.velodyne->header.seq;
  173. msg.header.stamp = virtualscan.velodyne->header.stamp;
  174. msg.angle_min = -PI;
  175. msg.angle_max = PI;
  176. msg.angle_increment = density;
  177. msg.time_increment = 0;
  178. msg.scan_time = 0.1;
  179. msg.range_min = 0.1;
  180. msg.range_max = 100;
  181. msg.ranges.resize(BEAMNUM);
  182. msg.intensities.resize(BEAMNUM);
  183. for (int i = 0; i < BEAMNUM; i++)
  184. {
  185. msg.ranges[i] = beams[i];
  186. msg.intensities[i] = 255;
  187. }
  188. scanros->sendMessage(msg);
  189. }
  190. #ifdef DEBUG_GUI
  191. drawGrid();
  192. drawPoints();
  193. showMatrixSlot(ui->comboBox->currentIndex());
  194. #endif
  195. }
  196. QPointF MainWindow::convert2RealPoint(QPoint point)
  197. {
  198. QPointF result;
  199. double ratio = 2 * MAXRANGE / IMAGESIZE;
  200. result.setX((IMAGESIZE / 2.0 - point.y()) * ratio);
  201. result.setY((IMAGESIZE / 2.0 - point.x()) * ratio);
  202. return result;
  203. }
  204. QPoint MainWindow::convert2ImagePoint(QPointF point)
  205. {
  206. QPoint result;
  207. double ratio = IMAGESIZE / (2 * MAXRANGE);
  208. result.setX(int(IMAGESIZE / 2.0 - point.y() * ratio + 0.5));
  209. result.setY(int(IMAGESIZE / 2.0 - point.x() * ratio + 0.5));
  210. return result;
  211. }
  212. void MainWindow::drawGrid()
  213. {
  214. image.fill(QColor(255, 255, 255));
  215. QPainter painter;
  216. painter.begin(&image);
  217. painter.setPen(QColor(128, 128, 128));
  218. QPoint center(IMAGESIZE / 2, IMAGESIZE / 2);
  219. double gridstep = (GRIDSIZE / MAXRANGE) * (IMAGESIZE / 2);
  220. for (int i = gridstep; i <= IMAGESIZE / 2; i += gridstep)
  221. {
  222. painter.drawEllipse(center, i, i);
  223. }
  224. painter.end();
  225. ui->label->setPixmap(QPixmap::fromImage(image));
  226. }
  227. void MainWindow::drawPoints()
  228. {
  229. QPainter painter;
  230. painter.begin(&image);
  231. painter.setPen(QColor(255, 0, 0));
  232. double PI = 3.141592654;
  233. double density = 2 * PI / BEAMNUM;
  234. for (int i = 0; i < BEAMNUM; i++)
  235. {
  236. double theta = i * density - PI;
  237. QPoint point = convert2ImagePoint(QPointF(beams[i] * cos(theta), beams[i] * sin(theta)));
  238. painter.drawEllipse(point, 1, 1);
  239. }
  240. painter.end();
  241. ui->label->setPixmap(QPixmap::fromImage(image));
  242. }
  243. void MainWindow::drawBeam(int beamid)
  244. {
  245. drawGrid();
  246. drawPoints();
  247. if (beamid >= BEAMNUM)
  248. {
  249. return;
  250. }
  251. QPainter painter;
  252. painter.begin(&image);
  253. painter.setPen(QColor(0, 0, 255));
  254. QPoint center(IMAGESIZE / 2, IMAGESIZE / 2);
  255. double PI = 3.141592654;
  256. double density = 2 * PI / BEAMNUM;
  257. double theta = beamid * density - PI;
  258. QPoint point = convert2ImagePoint(QPointF(beams[beamid] * cos(theta), beams[beamid] * sin(theta)));
  259. painter.drawLine(center, point);
  260. painter.end();
  261. ui->label->setPixmap(QPixmap::fromImage(image));
  262. }