网站建设教程.,wordpress 标题空格,中国公路建设行业协会网站上,静态网站开发常用语言CuraEngine之代码阅读#xff08;1#xff09;之路径优化函数#xff08;全#xff09; 注#xff1a;整理一些突然学到的C知识#xff0c;随时mark一下 例如#xff1a;忘记的关键字用法#xff0c;新关键字#xff0c;新数据结构 C 的 STL CuraEngine之代码阅读1之路径优化函数全 注整理一些突然学到的C知识随时mark一下 例如忘记的关键字用法新关键字新数据结构 C 的 STL CuraEngine之代码阅读1之路径优化函数全一、路径优化函数1、完整代码来自于CuraEngine源码 总结 提示本文为curaengine 中 路径优化函数代码 CuraEngine的功能用于3D打印接受STL文件或其他格式的文件如AMF文件作为输入并输出G代码GCode。G代码类似于汇编代码可以直接在底层硬件上运行控制电机等运动单元动作。
一、路径优化函数
1、完整代码来自于CuraEngine源码
void PathOrderOptimizer::optimize()
{// NOTE: Keep this vector fixed-size, it replaces an (non-standard, sized at runtime) array:std::vectorbool picked(polygons.size(), false);loc_to_line nullptr;for (unsigned poly_idx 0; poly_idx polygons.size(); poly_idx) /// find closest point to initial starting point within each polygon initialize picked{const ConstPolygonRef poly *polygons[poly_idx];switch (config.type){case EZSeamType::USER_SPECIFIED:polyStart.push_back(getClosestPointInPolygon(config.pos, poly_idx));break;case EZSeamType::RANDOM:polyStart.push_back(getRandomPointInPolygon(poly_idx));break;case EZSeamType::SHARPEST_CORNER:case EZSeamType::SHORTEST:default:polyStart.push_back(getClosestPointInPolygon(startPoint, poly_idx));break;}assert(poly.size() ! 2);}Point prev_point;switch (config.type){case EZSeamType::USER_SPECIFIED:prev_point config.pos;break;case EZSeamType::RANDOM: //TODO: Starting position of the first polygon isnt random.case EZSeamType::SHARPEST_CORNER:case EZSeamType::SHORTEST:default:prev_point startPoint;}for (unsigned int poly_order_idx 0; poly_order_idx polygons.size(); poly_order_idx) /// actual path order optimizer{int best_poly_idx -1;float bestDist2 std::numeric_limitsfloat::infinity();for (unsigned int poly_idx 0; poly_idx polygons.size(); poly_idx){if (picked[poly_idx] || polygons[poly_idx]-size() 1) /// skip single-point-polygons{continue;}assert (polygons[poly_idx]-size() ! 2);const Point p (*polygons[poly_idx])[polyStart[poly_idx]];float dist2 vSize2f(p - prev_point);if (dist2 bestDist2 combing_boundary){// using direct routing, this poly is the closest so far but as the combing boundary// is available see if the travel would cross the combing boundary and, if so, either get// the combed distance and use that instead or increase the distance to make it less attractiveif (PolygonUtils::polygonCollidesWithLineSegment(*combing_boundary, p, prev_point)){if ((polygons.size() - poly_order_idx) 100){// calculating the combing distance for lots of polygons is too time consuming so, instead,// just increase the distance to penalise travels that hit the combing boundarydist2 * 5;}else{if (!loc_to_line){// the combing boundary has been provided so do the initialisation// required to be able to calculate realistic travel distances to the start of new pathsconst int travel_avoid_distance 2000; // assume 2mm - not really critical for our purposesloc_to_line PolygonUtils::createLocToLineGrid(*combing_boundary, travel_avoid_distance);}CombPath comb_path;if (LinePolygonsCrossings::comb(*combing_boundary, *loc_to_line, p, prev_point, comb_path, -40, 0, false)){float dist 0;Point last_point p;for (const Point comb_point : comb_path){dist vSize(comb_point - last_point);last_point comb_point;}dist2 dist * dist;}}}}if (dist2 bestDist2){best_poly_idx poly_idx;bestDist2 dist2;}}if (best_poly_idx -1) /// should always be true; we should have been able to identify the best next polygon{assert(polygons[best_poly_idx]-size() ! 2);prev_point (*polygons[best_poly_idx])[polyStart[best_poly_idx]];picked[best_poly_idx] true;polyOrder.push_back(best_poly_idx);}else{logError(Failed to find next closest polygon.\n);}}if (loc_to_line ! nullptr){delete loc_to_line;}
}这段代码是一个名为PathOrderOptimizer::optimize()的函数它的主要目的是优化多边形路径的顺序gcode打印顺序。以下是代码的分段讲解
1、初始化一个布尔类型的向量picked用于记录每个多边形是否已被选中。向量的大小与多边形的数量相同初始值都为false。
std::vectorbool picked(polygons.size(), false);2、将loc_to_line指针设置为nullptr。
loc_to_line nullptr;3、遍历所有多边形根据配置类型config.type确定每个多边形的起始点polyStart。本人创造的逻辑简略标记for each polygon in polygons to polyStart遍历循环向量中的每个元最后为了得到polyStart。
for (unsigned poly_idx 0; poly_idx polygons.size(); poly_idx) {const ConstPolygonRef poly *polygons[poly_idx];switch (config.type) {case EZSeamType::USER_SPECIFIED:polyStart.push_back(getClosestPointInPolygon(config.pos, poly_idx));break;case EZSeamType::RANDOM:polyStart.push_back(getRandomPointInPolygon(poly_idx));break;case EZSeamType::SHARPEST_CORNER:case EZSeamType::SHORTEST:default:polyStart.push_back(getClosestPointInPolygon(startPoint, poly_idx));break;}assert(poly.size() ! 2);
}4、根据配置类型更新上一个点的位置prev_point。
switch (config.type) {case EZSeamType::USER_SPECIFIED:prev_point config.pos;break;case EZSeamType::RANDOM: //TODO: Starting position of the first polygon isnt random.case EZSeamType::SHARPEST_CORNER:case EZSeamType::SHORTEST:default:prev_point startPoint;
}5、第二层循环遍历所有多边形寻找距离上一个点prev_point最短邻的多边形。在这个过程中会跳过单点多边形和已经被选中的多边形。对于每个多边形计算其起始点到上一个点prevpoint的距离平方dist2。如果当前多边形与上一个点之间的距离小于之前找到的最佳距离并且存在边界限制combing_boundary则检查是否需要调整距离。 本人创造的逻辑简略标记for each polygon in polygons to bestDist bestpolyidx遍历循环向量中的每个元最后为了得到最优多边形
for (unsigned int poly_order_idx 0; poly_order_idx polygons.size(); poly_order_idx) {int best_poly_idx -1;float bestDist2 std::numeric_limitsfloat::infinity();for (unsigned int poly_idx 0; poly_idx polygons.size(); poly_idx) {if (picked[poly_idx] || polygons[poly_idx]-size() 1) {continue;}assert (polygons[poly_idx]-size() ! 2);const Point p (*polygons[poly_idx])[polyStart[poly_idx]];float dist2 vSize2f(p - prev_point);if (dist2 bestDist2 combing_boundary) {// ...省略部分代码...}if (dist2 bestDist2) {best_poly_idx poly_idx;bestDist2 dist2;}}6、条件语句根据best_poly_idx的值进行不同的操作。如果best_poly_idx大于-1表示找到了最接近的多边形索引。然后通过断言assert确保该多边形的大小不为2。接下来将prev_point更新为本次比较后得到的最优的多边形的起始点即(*polygons[best_poly_idx])[polyStart[best_poly_idx]]。然后将picked[best_poly_idx]标记为true表示已经选择了该多边形。最后将best_poly_idx添加到polyOrder向量中用于记录选择的多边形顺序。
如果best_poly_idx小于等于-1表示没有找到最close即距离最短的多边形。在这种情况下会调用logError函数输出错误信息“Failed to find next closest polygon.”
if (best_poly_idx -1) {assert(polygons[best_poly_idx]-size() ! 2);prev_point (*polygons[best_poly_idx])[polyStart[best_poly_idx]];picked[best_poly_idx] true;polyOrder.push_back(best_poly_idx);
} else {logError(Failed to find next closest polygon.\n);
}最后如果loc_to_line不为空则删掉它。
if (loc_to_line ! nullptr) {delete loc_to_line;
}总结
PathOrderOptimizer::optimize()的函数的主要目的是优化多边形路径的顺序。以下是代码的步骤总结 初始化一个布尔类型的向量picked用于记录每个多边形是否已被选中。向量的大小与多边形的数量相同初始值都为false。 将loc_to_line指针设置为nullptr。 遍历所有多边形根据配置类型config.type确定每个多边形的起始点polyStart。 根据配置类型设置上一个点prev_point。 遍历所有多边形寻找距离上一个点最近的多边形。在这个过程中会跳过单点多边形和已经被选中的多边形。 对于每个多边形计算其起始点到上一个点的距离平方dist2。如果当前多边形与上一个点之间的距离小于之前找到的最佳距离并且存在边界限制combing_boundary则检查是否需要调整距离。 如果找到了距离上一个点最近的多边形将其索引best_poly_idx添加到路径顺序向量polyOrder中并将对应的picked值设为true。 最后如果loc_to_line不为空则删掉它。